18b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project/* Copyright (C) 2006-2008 The Android Open Source Project
28b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project**
38b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project** This software is licensed under the terms of the GNU General Public
48b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project** License version 2, as published by the Free Software Foundation, and
58b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project** may be copied, distributed, and modified under those terms.
68b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project**
78b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project** This program is distributed in the hope that it will be useful,
88b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project** but WITHOUT ANY WARRANTY; without even the implied warranty of
98b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project** MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
108b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project** GNU General Public License for more details.
118b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project*/
128b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
138b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include <signal.h>
148b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include <unistd.h>
158b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include <string.h>
168b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include <sys/time.h>
178b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#ifdef _WIN32
188b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include <process.h>
198b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#endif
207fbf49776a98847a5f95325646f7eb5ff787423fVladimir Chtchetkine
218b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "sockets.h"
228b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
238b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/android.h"
248b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "qemu-common.h"
258b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "sysemu.h"
268b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "console.h"
2734f2974ce7ec7c71beb47b5daf9089d5c8c40c79David 'Digit' Turner#include "user-events.h"
288b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
298b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include <SDL.h>
308b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include <SDL_syswm.h>
318b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
328b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "math.h"
338b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
348b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/charmap.h"
358b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/utils/debug.h"
368b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/config.h"
378b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/config/config.h"
388b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
398b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/user-config.h"
408b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/utils/bufprint.h"
4126d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner#include "android/utils/filelock.h"
420a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner#include "android/utils/lineinput.h"
438b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/utils/path.h"
44622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner#include "android/utils/tempfile.h"
458b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
46f845627c83ce6ce3e306f9b6842d1e30ef89ae97David 'Digit' Turner#include "android/main-common.h"
478b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/help.h"
488b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "hw/goldfish_nand.h"
498b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
508b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#include "android/globals.h"
518b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
52fc8ed80ba1362d2ce500003625e1c9c39f765661Xavier Ducrohet#include "android/qemulator.h"
53055ae42d36d9d78a7920f66ee2df485d81d24264David 'Digit' Turner#include "android/display.h"
540119362f0d74ca74f3ea743f6e0e527a9edcc474Vladimir Chtchetkine
55ae835acc2d1a8b4aaeb599add9cfc02ea5789eafOt ten Thije#include "android/snapshot.h"
56ae835acc2d1a8b4aaeb599add9cfc02ea5789eafOt ten Thije
57e3fdd075ed97085b4201cb0c79609633b19bddccDavid 'Digit' Turner#include "android/framebuffer.h"
589a33e8554225c82cd900208f88e8965bb085ab87Vladimir Chtchetkine#include "iolooper.h"
59055ae42d36d9d78a7920f66ee2df485d81d24264David 'Digit' Turner
608b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source ProjectAndroidRotation  android_framebuffer_rotation;
618b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
628b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#define  STRINGIFY(x)   _STRINGIFY(x)
638b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#define  _STRINGIFY(x)  #x
648b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
65a383d02cb57dd7dadd382654175e51354073a139David 'Digit' Turner#ifdef ANDROID_SDK_TOOLS_REVISION
66a383d02cb57dd7dadd382654175e51354073a139David 'Digit' Turner#  define  VERSION_STRING  STRINGIFY(ANDROID_SDK_TOOLS_REVISION)".0"
67a383d02cb57dd7dadd382654175e51354073a139David 'Digit' Turner#else
68a383d02cb57dd7dadd382654175e51354073a139David 'Digit' Turner#  define  VERSION_STRING  "standalone"
69a383d02cb57dd7dadd382654175e51354073a139David 'Digit' Turner#endif
708b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
718b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#define  D(...)  do {  if (VERBOSE_CHECK(init)) dprint(__VA_ARGS__); } while (0)
728b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
738b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectextern int  control_console_start( int  port );  /* in control.c */
748b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
758b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectextern int qemu_milli_needed;
768b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
778b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project/* the default device DPI if none is specified by the skin
788b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project */
798b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#define  DEFAULT_DEVICE_DPI  165
808b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
818b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#ifdef CONFIG_TRACE
828b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectextern void  start_tracing(void);
838b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectextern void  stop_tracing(void);
848b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#endif
858b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
868b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectunsigned long   android_verbose;
878b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
888b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectint qemu_main(int argc, char **argv);
898b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
908b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project/* this function dumps the QEMU help */
918b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectextern void  help( void );
928b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectextern void  emulator_help( void );
938b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
948b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#define  VERBOSE_OPT(str,var)   { str, &var }
958b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
968b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#define  _VERBOSE_TAG(x,y)   { #x, VERBOSE_##x, y },
978b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectstatic const struct { const char*  name; int  flag; const char*  text; }
988b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectverbose_options[] = {
998b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    VERBOSE_TAG_LIST
1008b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    { 0, 0, 0 }
1018b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project};
1028b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
1038b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectvoid emulator_help( void )
1048b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project{
1058b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    STRALLOC_DEFINE(out);
1068b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    android_help_main(out);
1078b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    printf( "%.*s", out->n, out->s );
1088b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    stralloc_reset(out);
1098b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    exit(1);
1108b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project}
1118b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
11240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner/* TODO: Put in shared source file */
11340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turnerstatic char*
11440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner_getFullFilePath( const char* rootPath, const char* fileName )
11540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner{
11640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    if (path_is_absolute(fileName)) {
11740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        return ASTRDUP(fileName);
11840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    } else {
11940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        char temp[PATH_MAX], *p=temp, *end=p+sizeof(temp);
12040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
12140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        p = bufprint(temp, end, "%s/%s", rootPath, fileName);
12240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (p >= end) {
12340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            return NULL;
12440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        }
12540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        return ASTRDUP(temp);
12640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    }
12740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner}
12840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
12940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turnerstatic uint64_t
13040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner_adjustPartitionSize( const char*  description,
13140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                      uint64_t     imageBytes,
13240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                      uint64_t     defaultBytes,
13340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                      int          inAndroidBuild )
13440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner{
13540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    char      temp[64];
13640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    unsigned  imageMB;
13740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    unsigned  defaultMB;
13840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
13940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    if (imageBytes <= defaultBytes)
14040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        return defaultBytes;
14140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
14240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    imageMB   = convertBytesToMB(imageBytes);
14340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    defaultMB = convertBytesToMB(defaultBytes);
14440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
14540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    if (imageMB > defaultMB) {
14640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        snprintf(temp, sizeof temp, "(%d MB > %d MB)", imageMB, defaultMB);
14740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    } else {
148c7389bd69e570a2c8432b37399aff1976b021f0fAndrew Hsieh        snprintf(temp, sizeof temp, "(%" PRIu64 "  bytes > %" PRIu64 " bytes)", imageBytes, defaultBytes);
14940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    }
15040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
15140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    if (inAndroidBuild) {
15240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        dwarning("%s partition size adjusted to match image file %s\n", description, temp);
15340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    }
15440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
15540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    return convertMBToBytes(imageMB);
15640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner}
15740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
1588b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Projectint main(int argc, char **argv)
1598b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project{
1608b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    char   tmp[MAX_PATH];
1618b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    char*  tmpend = tmp + sizeof(tmp);
1628b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    char*  args[128];
1638b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    int    n;
1648b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    char*  opt;
1655e736937d49affc9131944d7c879246fbcba3b70David 'Digit' Turner    /* The emulator always uses the first serial port for kernel messages
1665e736937d49affc9131944d7c879246fbcba3b70David 'Digit' Turner     * and the second one for qemud. So start at the third if we need one
1675e736937d49affc9131944d7c879246fbcba3b70David 'Digit' Turner     * for logcat or 'shell'
1685e736937d49affc9131944d7c879246fbcba3b70David 'Digit' Turner     */
1695e736937d49affc9131944d7c879246fbcba3b70David 'Digit' Turner    int    serial = 2;
1708b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    int    shell_serial = 0;
1718b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
1722ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner    int    forceArmv7 = 0;
1732ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner
1748b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    AndroidHwConfig*  hw;
175cd059b15f2c7df69f4a087bd66900eb172e41d1cDavid 'Digit' Turner    AvdInfo*          avd;
17674d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner    AConfig*          skinConfig;
17774d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner    char*             skinPath;
17883ffd66e78d290aa054ace5e484ae3766f638390Vladimir Chtchetkine    int               inAndroidBuild;
17988078b8875dab47abf9fe80488503f60d9835eafVladimir Chtchetkine    uint64_t          defaultPartitionSize = convertMBToBytes(200);
1808b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
1818b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    AndroidOptions  opts[1];
182b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    /* net.shared_net_ip boot property value. */
183b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    char boot_prop_ip[64];
184b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    boot_prop_ip[0] = '\0';
1858b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
1868b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    args[0] = argv[0];
1878b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
1888b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if ( android_parse_options( &argc, &argv, opts ) < 0 ) {
1898b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        exit(1);
1908b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
1918b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
192bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner#ifdef _WIN32
193bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner    socket_init();
194bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner#endif
195bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner
196bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner    handle_ui_options(opts);
197bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner
1988b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    while (argc-- > 1) {
1998b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        opt = (++argv)[0];
2008b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2018b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if(!strcmp(opt, "-qemu")) {
2028b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            argc--;
2038b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            argv++;
2048b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            break;
2058b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
2068b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2078b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (!strcmp(opt, "-help")) {
2088b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            emulator_help();
2098b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
2108b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2118b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (!strncmp(opt, "-help-",6)) {
2128b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            STRALLOC_DEFINE(out);
2138b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            opt += 6;
2148b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2158b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            if (!strcmp(opt, "all")) {
2168b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                android_help_all(out);
2178b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            }
2188b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            else if (android_help_for_option(opt, out) == 0) {
2198b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                /* ok */
2208b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            }
2218b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            else if (android_help_for_topic(opt, out) == 0) {
2228b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                /* ok */
2238b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            }
2248b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            if (out->n > 0) {
2258b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                printf("\n%.*s", out->n, out->s);
2268b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                exit(0);
2278b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            }
2288b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2298b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            fprintf(stderr, "unknown option: -help-%s\n", opt);
2308b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            fprintf(stderr, "please use -help for a list of valid topics\n");
2318b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            exit(1);
2328b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
2338b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2348b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (opt[0] == '-') {
2358b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            fprintf(stderr, "unknown option: %s\n", opt);
2368b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            fprintf(stderr, "please use -help for a list of valid options\n");
2378b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            exit(1);
2388b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
2398b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2408b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        fprintf(stderr, "invalid command-line parameter: %s.\n", opt);
2418b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        fprintf(stderr, "Hint: use '@foo' to launch a virtual device named 'foo'.\n");
2428b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        fprintf(stderr, "please use -help for more information\n");
2438b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        exit(1);
2448b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
2458b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2468b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (opts->version) {
2478b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        printf("Android emulator version %s\n"
2485f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner               "Copyright (C) 2006-2011 The Android Open Source Project and many others.\n"
2498b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               "This program is a derivative of the QEMU CPU emulator (www.qemu.org).\n\n",
2508b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#if defined ANDROID_BUILD_ID
2518b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               VERSION_STRING " (build_id " STRINGIFY(ANDROID_BUILD_ID) ")" );
2528b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#else
2538b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               VERSION_STRING);
2548b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#endif
2558b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        printf("  This software is licensed under the terms of the GNU General Public\n"
2568b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               "  License version 2, as published by the Free Software Foundation, and\n"
2578b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               "  may be copied, distributed, and modified under those terms.\n\n"
2588b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               "  This program is distributed in the hope that it will be useful,\n"
2598b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               "  but WITHOUT ANY WARRANTY; without even the implied warranty of\n"
2608b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               "  MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the\n"
2618b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project               "  GNU General Public License for more details.\n\n");
2628b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2638b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        exit(0);
2648b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
2658b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
2665f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    if (opts->snapshot_list) {
267d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner        if (opts->snapstorage == NULL) {
268d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner            /* Need to find the default snapstorage */
269d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner            avd = createAVD(opts, &inAndroidBuild);
270d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner            opts->snapstorage = avdInfo_getSnapStoragePath(avd);
271d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner            if (opts->snapstorage != NULL) {
272d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner                D("autoconfig: -snapstorage %s", opts->snapstorage);
273d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner            } else {
274d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner                if (inAndroidBuild) {
275d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner                    derror("You must use the -snapstorage <file> option to specify a snapshot storage file!\n");
276d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner                } else {
277d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner                    derror("This AVD doesn't have snapshotting enabled!\n");
278d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner                }
279d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner                exit(1);
280d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner            }
281d80a7861fe5e21e3dcb80480a77b033e6b307dd5David 'Digit' Turner        }
2825f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        snapshot_print_and_exit(opts->snapstorage);
2835f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    }
2845f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
28525eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner    sanitizeOptions(opts);
28625eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner
287bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner    /* Initialization of UI started with -attach-core should work differently
288bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner     * than initialization of UI that starts the core. In particular....
289bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner     */
290bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner
291bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner    /* -charmap is incompatible with -attach-core, because particular
292bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner     * charmap gets set up in the running core. */
29374d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner    if (android_charmap_setup(opts->charmap)) {
29474d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner        exit(1);
2958b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
2968b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
29783ffd66e78d290aa054ace5e484ae3766f638390Vladimir Chtchetkine    /* Parses options and builds an appropriate AVD. */
298462564f31bbdc9939bf1d2376e2782defa7ef655David 'Digit' Turner    avd = android_avdInfo = createAVD(opts, &inAndroidBuild);
299cd059b15f2c7df69f4a087bd66900eb172e41d1cDavid 'Digit' Turner
3008b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    /* get the skin from the virtual device configuration */
30125eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner    if (opts->skindir != NULL) {
30225eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        if (opts->skin == NULL) {
30325eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner            /* NOTE: Normally handled by sanitizeOptions(), just be safe */
30425eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner            derror("The -skindir <path> option requires a -skin <name> option");
30525eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner            exit(2);
30625eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        }
30725eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner    } else {
30825eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        char* skinName;
30925eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        char* skinDir;
3108b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
31125eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        avdInfo_getSkinInfo(avd, &skinName, &skinDir);
31225eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner
31325eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        if (opts->skin == NULL) {
31425eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner            opts->skin = skinName;
31525eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner            D("autoconfig: -skin %s", opts->skin);
31625eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        } else {
31725eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner            AFREE(skinName);
31825eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        }
31925eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner
32025eb6557b94da066d6e137c07aeced39badf5aa6David 'Digit' Turner        opts->skindir = skinDir;
3218b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        D("autoconfig: -skindir %s", opts->skindir);
322689d1147b1994be1d8e33ee4d1a8ec76742bb4a6Xavier Ducrohet
323689d1147b1994be1d8e33ee4d1a8ec76742bb4a6Xavier Ducrohet        /* update the avd hw config from this new skin */
324689d1147b1994be1d8e33ee4d1a8ec76742bb4a6Xavier Ducrohet        avdInfo_getSkinHardwareIni(avd, opts->skin, opts->skindir);
3258b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
3268b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
3278b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    /* Read hardware configuration */
3288b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    hw = android_hw;
329b64325d15d9e767c652491414c95f4fc148b0211David 'Digit' Turner    if (avdInfo_initHwConfig(avd, hw) < 0) {
3308b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        derror("could not read hardware configuration ?");
3318b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        exit(1);
3328b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
3338b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
3348b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (opts->keyset) {
3358b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        parse_keyset(opts->keyset, opts);
3368b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (!android_keyset) {
3378b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            fprintf(stderr,
3388b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                    "emulator: WARNING: could not find keyset file named '%s',"
3398b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                    " using defaults instead\n",
3408b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                    opts->keyset);
3418b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
3428b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
3438b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (!android_keyset) {
3448b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        parse_keyset("default", opts);
3458b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (!android_keyset) {
3468b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            android_keyset = skin_keyset_new_from_text( skin_keyset_get_default() );
3478b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            if (!android_keyset) {
3488b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                fprintf(stderr, "PANIC: default keyset file is corrupted !!\n" );
3498b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                fprintf(stderr, "PANIC: please update the code in android/skin/keyset.c\n" );
3508b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                exit(1);
3518b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            }
3528b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            if (!opts->keyset)
3538b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                write_default_keyset();
3548b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
3558b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
3568b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
35740beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie    if (opts->shared_net_id) {
35840beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        char*  end;
35940beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        long   shared_net_id = strtol(opts->shared_net_id, &end, 0);
36040beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        if (end == NULL || *end || shared_net_id < 1 || shared_net_id > 255) {
36140beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie            fprintf(stderr, "option -shared-net-id must be an integer between 1 and 255\n");
36240beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie            exit(1);
36340beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        }
364b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine        snprintf(boot_prop_ip, sizeof(boot_prop_ip),
365b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine                 "net.shared_net_ip=10.1.2.%ld", shared_net_id);
36640beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie    }
36740beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie
36840beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie
369755811e67c266333807571f798b62b6916611f87David 'Digit' Turner    user_config_init();
3702507cab8a78fb609461a2b9cc4708bab60fc53a4David 'Digit' Turner    parse_skin_files(opts->skindir, opts->skin, opts, hw,
37174d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner                     &skinConfig, &skinPath);
3728b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
373092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner    if (!opts->netspeed && skin_network_speed) {
374092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner        D("skin network speed: '%s'", skin_network_speed);
375092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner        if (strcmp(skin_network_speed, NETWORK_SPEED_DEFAULT) != 0) {
376092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner            opts->netspeed = (char*)skin_network_speed;
377092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner        }
3788b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
379092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner    if (!opts->netdelay && skin_network_delay) {
380092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner        D("skin network delay: '%s'", skin_network_delay);
381092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner        if (strcmp(skin_network_delay, NETWORK_DELAY_DEFAULT) != 0) {
382092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner            opts->netdelay = (char*)skin_network_delay;
383092361e19ecc2992965729538984354099eea8cbDavid 'Digit' Turner        }
3848b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
3858b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
3868b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (opts->trace) {
387cd059b15f2c7df69f4a087bd66900eb172e41d1cDavid 'Digit' Turner        char*   tracePath = avdInfo_getTracePath(avd, opts->trace);
3888b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        int     ret;
3898b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
3908b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (tracePath == NULL) {
3918b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            derror( "bad -trace parameter" );
3928b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            exit(1);
3938b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
3948b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        ret = path_mkdir_if_needed( tracePath, 0755 );
3958b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (ret < 0) {
3968b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            fprintf(stderr, "could not create directory '%s'\n", tmp);
3978b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            exit(2);
3988b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
3998b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        opts->trace = tracePath;
4008b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
4018b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
40233f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine    /* Update CPU architecture for HW configs created from build dir. */
40333f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine    if (inAndroidBuild) {
40433f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine#if defined(TARGET_ARM)
40533f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine        free(android_hw->hw_cpu_arch);
40633f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine        android_hw->hw_cpu_arch = ASTRDUP("arm");
40733f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine#elif defined(TARGET_I386)
40833f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine        free(android_hw->hw_cpu_arch);
40933f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine        android_hw->hw_cpu_arch = ASTRDUP("x86");
410741dc13597ac064e6a48bb2a6ec069cbc1cd0dbbBhanu Chetlapalli#elif defined(TARGET_MIPS)
411741dc13597ac064e6a48bb2a6ec069cbc1cd0dbbBhanu Chetlapalli        free(android_hw->hw_cpu_arch);
412741dc13597ac064e6a48bb2a6ec069cbc1cd0dbbBhanu Chetlapalli        android_hw->hw_cpu_arch = ASTRDUP("mips");
41333f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine#endif
41433f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine    }
41533f89d05b375f18596fa5892acaaae356fbb0c0eVladimir Chtchetkine
4168b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    n = 1;
4178b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    /* generate arguments for the underlying qemu main() */
418238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner    {
4190b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        char*  kernelFile    = opts->kernel;
4200b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        int    kernelFileLen;
4210b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner
4220b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        if (kernelFile == NULL) {
4230b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner            kernelFile = avdInfo_getKernelPath(avd);
4240b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner            if (kernelFile == NULL) {
4250b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner                derror( "This AVD's configuration is missing a kernel file!!" );
4260b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner                exit(2);
4270b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner            }
4280b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner            D("autoconfig: -kernel %s", kernelFile);
4290b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        }
4300b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        if (!path_exists(kernelFile)) {
4310b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner            derror( "Invalid or missing kernel image file: %s", kernelFile );
4320b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner            exit(2);
4330b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        }
434238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner
4350b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        hw->kernel_path = kernelFile;
436238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner
437238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner        /* If the kernel image name ends in "-armv7", then change the cpu
438238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * type automatically. This is a poor man's approach to configuration
439238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * management, but should allow us to get past building ARMv7
440238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * system images with dex preopt pass without introducing too many
441238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * changes to the emulator sources.
442238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         *
443238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * XXX:
444238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * A 'proper' change would require adding some sort of hardware-property
445238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * to each AVD config file, then automatically determine its value for
446238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * full Android builds (depending on some environment variable), plus
447238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * some build system changes. I prefer not to do that for now for reasons
448238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         * of simplicity.
449238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         */
4500b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner         kernelFileLen = strlen(kernelFile);
451238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         if (kernelFileLen > 6 && !memcmp(kernelFile + kernelFileLen - 6, "-armv7", 6)) {
4522ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner             forceArmv7 = 1;
453238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner         }
454238b4b0ef1a01afa66ef267dae4a96401ad386dbDavid 'Digit' Turner    }
4558b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
456b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    if (boot_prop_ip[0]) {
457b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine        args[n++] = "-boot-property";
458b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine        args[n++] = boot_prop_ip;
459b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    }
460b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine
461318f17a0050e729bce8545463b657c1d62835b5eVladimir Chtchetkine    if (opts->tcpdump) {
462318f17a0050e729bce8545463b657c1d62835b5eVladimir Chtchetkine        args[n++] = "-tcpdump";
463318f17a0050e729bce8545463b657c1d62835b5eVladimir Chtchetkine        args[n++] = opts->tcpdump;
464318f17a0050e729bce8545463b657c1d62835b5eVladimir Chtchetkine    }
465318f17a0050e729bce8545463b657c1d62835b5eVladimir Chtchetkine
466e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine#ifdef CONFIG_NAND_LIMITS
467e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    if (opts->nand_limits) {
468e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine        args[n++] = "-nand-limits";
469e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine        args[n++] = opts->nand_limits;
470e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    }
471e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine#endif
472e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine
47374d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner    if (opts->timezone) {
47474d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner        args[n++] = "-timezone";
47574d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner        args[n++] = opts->timezone;
47674d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner    }
47774d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner
478e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    if (opts->netspeed) {
479e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine        args[n++] = "-netspeed";
480e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine        args[n++] = opts->netspeed;
481e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    }
482e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    if (opts->netdelay) {
483e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine        args[n++] = "-netdelay";
484e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine        args[n++] = opts->netdelay;
485e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    }
486e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    if (opts->netfast) {
487e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine        args[n++] = "-netfast";
488e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine    }
489e13168648d5947955e0fd4fbf396f891ae53921fVladimir Chtchetkine
490b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine    if (opts->audio) {
491b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine        args[n++] = "-audio";
492b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine        args[n++] = opts->audio;
493b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine    }
494b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine
495b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine    if (opts->cpu_delay) {
496b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine        args[n++] = "-cpu-delay";
497b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine        args[n++] = opts->cpu_delay;
498b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine    }
499b2438402d16ee4a0bb4b077d0ad0ef1d82b2a08cVladimir Chtchetkine
5007fbf49776a98847a5f95325646f7eb5ff787423fVladimir Chtchetkine    if (opts->dns_server) {
5017fbf49776a98847a5f95325646f7eb5ff787423fVladimir Chtchetkine        args[n++] = "-dns-server";
5027fbf49776a98847a5f95325646f7eb5ff787423fVladimir Chtchetkine        args[n++] = opts->dns_server;
5037fbf49776a98847a5f95325646f7eb5ff787423fVladimir Chtchetkine    }
5047fbf49776a98847a5f95325646f7eb5ff787423fVladimir Chtchetkine
5059ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner    /* opts->ramdisk is never NULL (see createAVD) here */
5069ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner    if (opts->ramdisk) {
5079ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner        AFREE(hw->disk_ramdisk_path);
5089ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner        hw->disk_ramdisk_path = ASTRDUP(opts->ramdisk);
5099ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner    }
5109ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner    else if (!hw->disk_ramdisk_path[0]) {
5119ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner        hw->disk_ramdisk_path = avdInfo_getRamdiskPath(avd);
5129ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner        D("autoconfig: -ramdisk %s", hw->disk_ramdisk_path);
5139ff69721d24f81317183ddb2e9e352bb34650752David 'Digit' Turner    }
5148b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
51540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    /* -partition-size is used to specify the max size of both the system
51640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner     * and data partition sizes.
51740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner     */
51840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    if (opts->partition_size) {
51940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        char*  end;
52040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        long   sizeMB = strtol(opts->partition_size, &end, 0);
52140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        long   minSizeMB = 10;
52240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        long   maxSizeMB = LONG_MAX / ONE_MB;
52340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
52440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (sizeMB < 0 || *end != 0) {
52540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            derror( "-partition-size must be followed by a positive integer" );
52640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            exit(1);
52740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        }
52840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (sizeMB < minSizeMB || sizeMB > maxSizeMB) {
52940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            derror( "partition-size (%d) must be between %dMB and %dMB",
53040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                    sizeMB, minSizeMB, maxSizeMB );
53140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            exit(1);
53240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        }
53340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        defaultPartitionSize = (uint64_t) sizeMB * ONE_MB;
53440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    }
53540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
53640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
53740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    /** SYSTEM PARTITION **/
53840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
53940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    if (opts->sysdir == NULL) {
54040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (avdInfo_inAndroidBuild(avd)) {
54140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            opts->sysdir = ASTRDUP(avdInfo_getContentPath(avd));
54240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            D("autoconfig: -sysdir %s", opts->sysdir);
54340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        }
54440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    }
54540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
54640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    if (opts->sysdir != NULL) {
54740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (!path_exists(opts->sysdir)) {
54840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            derror("Directory does not exist: %s", opts->sysdir);
54940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            exit(1);
55040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        }
55140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    }
55240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
5538b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    {
55440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        char*  rwImage   = NULL;
55540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        char*  initImage = NULL;
55640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
55740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        do {
55840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            if (opts->system == NULL) {
55940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                /* If -system is not used, try to find a runtime system image
56040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                * (i.e. system-qemu.img) in the content directory.
56140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                */
56240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                rwImage = avdInfo_getSystemImagePath(avd);
56340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                if (rwImage != NULL) {
56440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                    break;
56540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                }
56640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                /* Otherwise, try to find the initial system image */
56740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                initImage = avdInfo_getSystemInitImagePath(avd);
56840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                if (initImage == NULL) {
56940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                    derror("No initial system image for this configuration!");
57040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                    exit(1);
57140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                }
57240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                break;
57340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            }
5748b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
57540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            /* If -system <name> is used, use it to find the initial image */
576ea2837728272b04bd236a74cd1ea547ec6f63c20David 'Digit' Turner            if (opts->sysdir != NULL && !path_exists(opts->system)) {
57740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                initImage = _getFullFilePath(opts->sysdir, opts->system);
57840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            } else {
57940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                initImage = ASTRDUP(opts->system);
58040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            }
58140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            if (!path_exists(initImage)) {
58240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                derror("System image file doesn't exist: %s", initImage);
58340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                exit(1);
58440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            }
5858b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
58640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        } while (0);
58740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
58840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (rwImage != NULL) {
58940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            /* Use the read/write image file directly */
59040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            hw->disk_systemPartition_path     = rwImage;
59140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            hw->disk_systemPartition_initPath = NULL;
59240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            D("Using direct system image: %s", rwImage);
59340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        } else if (initImage != NULL) {
59440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            hw->disk_systemPartition_path = NULL;
59540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            hw->disk_systemPartition_initPath = initImage;
59640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            D("Using initial system image: %s", initImage);
59740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        }
5988b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
59940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        /* Check the size of the system partition image.
60040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        * If we have an AVD, it must be smaller than
60140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        * the disk.systemPartition.size hardware property.
60240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        *
60340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        * Otherwise, we need to adjust the systemPartitionSize
60440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        * automatically, and print a warning.
60540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        *
60640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        */
60740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        const char* systemImage = hw->disk_systemPartition_path;
60840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        uint64_t    systemBytes;
60940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
61040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (systemImage == NULL)
61140841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            systemImage = hw->disk_systemPartition_initPath;
61240841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
61340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        if (path_get_size(systemImage, &systemBytes) < 0) {
61440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            derror("Missing system image: %s", systemImage);
61540841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            exit(1);
61640841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        }
61740841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
61840841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner        hw->disk_systemPartition_size =
61940841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner            _adjustPartitionSize("system", systemBytes, defaultPartitionSize,
62040841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner                                 avdInfo_inAndroidBuild(avd));
6218b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
6228b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
62340841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner    /** DATA PARTITION **/
62440841b2d221273a08abfe20824e7631211ade31dDavid 'Digit' Turner
625fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner    if (opts->datadir) {
626fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        if (!path_exists(opts->datadir)) {
627fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            derror("Invalid -datadir directory: %s", opts->datadir);
628fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        }
629fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner    }
630fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
631fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner    {
632fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        char*  dataImage = NULL;
633fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        char*  initImage = NULL;
634fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
635fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        do {
636fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            if (!opts->data) {
637fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                dataImage = avdInfo_getDataImagePath(avd);
638fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                if (dataImage != NULL) {
639fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                    D("autoconfig: -data %s", dataImage);
640fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                    break;
641fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                }
642fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                dataImage = avdInfo_getDefaultDataImagePath(avd);
643fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                if (dataImage == NULL) {
644fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                    derror("No data image path for this configuration!");
645fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                    exit (1);
646fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                }
647fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                opts->wipe_data = 1;
648fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                break;
649fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            }
6508b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
651fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            if (opts->datadir) {
652fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                dataImage = _getFullFilePath(opts->datadir, opts->data);
653fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            } else {
654fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                dataImage = ASTRDUP(opts->data);
655fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            }
656fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        } while (0);
657fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
658fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        if (opts->initdata != NULL) {
659fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            initImage = ASTRDUP(opts->initdata);
660fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            if (!path_exists(initImage)) {
661fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                derror("Invalid initial data image path: %s", initImage);
662fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                exit(1);
663fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            }
664fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        } else {
665fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            initImage = avdInfo_getDataInitImagePath(avd);
666fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            D("autoconfig: -initdata %s", initImage);
667fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        }
668fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
669fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        hw->disk_dataPartition_path = dataImage;
670fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        if (opts->wipe_data) {
671fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            hw->disk_dataPartition_initPath = initImage;
672fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        } else {
673fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            hw->disk_dataPartition_initPath = NULL;
674fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        }
675fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
676f758411e012389b1d9699e10cae6f1ac98cca419Maciek Molerus        uint64_t     defaultBytes =
677f758411e012389b1d9699e10cae6f1ac98cca419Maciek Molerus                hw->disk_dataPartition_size == 0 ?
678f758411e012389b1d9699e10cae6f1ac98cca419Maciek Molerus                defaultPartitionSize :
679d4f5a3ae87a7246613188940c1667bf2880da402Vladimir Chtchetkine                hw->disk_dataPartition_size;
680fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        uint64_t     dataBytes;
681fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        const char*  dataPath = hw->disk_dataPartition_initPath;
682fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
683fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        if (dataPath == NULL)
684fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            dataPath = hw->disk_dataPartition_path;
685fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
686fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        path_get_size(dataPath, &dataBytes);
687fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner
688fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner        hw->disk_dataPartition_size =
689fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner            _adjustPartitionSize("data", dataBytes, defaultBytes,
690fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner                                 avdInfo_inAndroidBuild(avd));
691fd59c330bec77e7b9241e478efb1e1c508480d1dDavid 'Digit' Turner    }
6928b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
693c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner    /** CACHE PARTITION **/
694c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner
695c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner    if (opts->no_cache) {
696c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        /* No cache partition at all */
697c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        hw->disk_cachePartition = 0;
6988b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
699c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner    else if (!hw->disk_cachePartition) {
700c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        if (opts->cache) {
701c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner            dwarning( "Emulated hardware doesn't support a cache partition. -cache option ignored!" );
702c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner            opts->cache = NULL;
703c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        }
7048b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
705c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner    else
706c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner    {
707c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        if (!opts->cache) {
708c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner            /* Find the current cache partition file */
709c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner            opts->cache = avdInfo_getCachePath(avd);
710c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner            if (opts->cache == NULL) {
711c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner                /* The file does not exists, we will force its creation
712c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner                 * if we are not in the Android build system. Otherwise,
713c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner                 * a temporary file will be used.
714c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner                 */
715c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner                if (!avdInfo_inAndroidBuild(avd)) {
716c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner                    opts->cache = avdInfo_getDefaultCachePath(avd);
717c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner                }
718c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner            }
71948a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            if (opts->cache) {
72048a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                D("autoconfig: -cache %s", opts->cache);
72148a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            }
722c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        }
7238b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
724c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        if (opts->cache) {
725c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner            hw->disk_cachePartition_path = ASTRDUP(opts->cache);
726c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner        }
7278b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
7288b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
7296f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine    if (hw->disk_cachePartition_path && opts->cache_size) {
7306f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine        /* Set cache partition size per user options. */
7316f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine        char*  end;
7326f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine        long   sizeMB = strtol(opts->cache_size, &end, 0);
7336f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine
7346f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine        if (sizeMB < 0 || *end != 0) {
7356f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine            derror( "-cache-size must be followed by a positive integer" );
7366f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine            exit(1);
7376f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine        }
7386f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine        hw->disk_cachePartition_size = (uint64_t) sizeMB * ONE_MB;
7396f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine    }
7406f50aa39e741a1d1f3081665d0b7f8d56b7b793cVladimir Chtchetkine
741c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner    /** SD CARD PARTITION */
742c480cca8d2007f5df62a7431beda310911b963e6David 'Digit' Turner
74348a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner    if (!hw->hw_sdCard) {
74448a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner        /* No SD Card emulation, so -sdcard will be ignored */
74548a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner        if (opts->sdcard) {
74648a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            dwarning( "Emulated hardware doesn't support SD Cards. -sdcard option ignored." );
74748a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            opts->sdcard = NULL;
74848a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner        }
74948a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner    } else {
75048a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner        /* Auto-configure -sdcard if it is not available */
75148a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner        if (!opts->sdcard) {
75248a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            do {
75348a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                /* If -datadir <path> is used, look for a sdcard.img file here */
75448a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                if (opts->datadir) {
75548a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                    bufprint(tmp, tmpend, "%s/%s", opts->datadir, "system.img");
75648a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                    if (path_exists(tmp)) {
75748a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                        opts->sdcard = strdup(tmp);
75848a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                        break;
75948a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                    }
76048a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                }
76148a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner
76248a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                /* Otherwise, look at the AVD's content */
76348a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                opts->sdcard = avdInfo_getSdCardPath(avd);
76448a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                if (opts->sdcard != NULL) {
76548a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                    break;
76648a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                }
76748a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner
76848a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                /* Nothing */
76948a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            } while (0);
77048a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner
77148a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            if (opts->sdcard) {
77248a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                D("autoconfig: -sdcard %s", opts->sdcard);
77348a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            }
77448a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner        }
7758b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
7768b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
7778b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if(opts->sdcard) {
7788b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        uint64_t  size;
7798b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (path_get_size(opts->sdcard, &size) == 0) {
7808b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            /* see if we have an sdcard image.  get its size if it exists */
7818b657e5deaa03b989b0b36791fcf2aa6b2882656David 'Digit' Turner            /* due to what looks like limitations of the MMC protocol, one has
7828b657e5deaa03b989b0b36791fcf2aa6b2882656David 'Digit' Turner             * to use an SD Card image that is equal or larger than 9 MB
7838b657e5deaa03b989b0b36791fcf2aa6b2882656David 'Digit' Turner             */
7848b657e5deaa03b989b0b36791fcf2aa6b2882656David 'Digit' Turner            if (size < 9*1024*1024ULL) {
7858b657e5deaa03b989b0b36791fcf2aa6b2882656David 'Digit' Turner                fprintf(stderr, "### WARNING: SD Card files must be at least 9MB, ignoring '%s'\n", opts->sdcard);
7868b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            } else {
78748a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner                hw->hw_sdCard_path = ASTRDUP(opts->sdcard);
7888b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            }
7898b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        } else {
79048a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner            dwarning("no SD Card image at '%s'", opts->sdcard);
7918b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
7928b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
7938b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
79448a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner
79548a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner    /** SNAPSHOT STORAGE HANDLING */
79648a3c66361158678f476fc7c2eca2bef025eae62David 'Digit' Turner
7975f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    /* Determine snapstorage path. -no-snapstorage disables all snapshotting
7985f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner     * support. This means you can't resume a snapshot at load, save it at
7995f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner     * exit, or even load/save them dynamically at runtime with the console.
8005f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner     */
8015f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    if (opts->no_snapstorage) {
8025f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8035f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        if (opts->snapshot) {
8045f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            dwarning("ignoring -snapshot option due to the use of -no-snapstorage");
8055f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            opts->snapshot = NULL;
8065f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        }
8075f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8085f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        if (opts->snapstorage) {
8095f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            dwarning("ignoring -snapstorage option due to the use of -no-snapstorage");
8105f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            opts->snapstorage = NULL;
8115f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        }
8125f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    }
8135f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    else
8145f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    {
815873c3cb5688092d2822837511cfb2b330d265801Vladimir Chtchetkine        if (!opts->snapstorage && avdInfo_getSnapshotPresent(avd)) {
8165f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            opts->snapstorage = avdInfo_getSnapStoragePath(avd);
8175f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            if (opts->snapstorage != NULL) {
8185f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner                D("autoconfig: -snapstorage %s", opts->snapstorage);
819353b3b1135563e2bcaf7797acfa35a2fe2d3a818Ot ten Thije            }
820353b3b1135563e2bcaf7797acfa35a2fe2d3a818Ot ten Thije        }
821353b3b1135563e2bcaf7797acfa35a2fe2d3a818Ot ten Thije
8225f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        if (opts->snapstorage && !path_exists(opts->snapstorage)) {
8235f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            D("no image at '%s', state snapshots disabled", opts->snapstorage);
8245f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            opts->snapstorage = NULL;
8255f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        }
8265f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    }
8275f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8285f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    /* If we have a valid snapshot storage path */
8295f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8305f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner    if (opts->snapstorage) {
8315f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8325f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        hw->disk_snapStorage_path = ASTRDUP(opts->snapstorage);
8335f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8345f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        /* -no-snapshot is equivalent to using both -no-snapshot-load
8355f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        * and -no-snapshot-save. You can still load/save snapshots dynamically
8365f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        * from the console though.
8375f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        */
8385f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        if (opts->no_snapshot) {
8395f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8405f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            opts->no_snapshot_load = 1;
8415f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            opts->no_snapshot_save = 1;
8425f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8435f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            if (opts->snapshot) {
8445f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner                dwarning("ignoring -snapshot option due to the use of -no-snapshot.");
84553d8a5c0c8fc087d16316a4399f5a773339c4956Tim Baverstock            }
8465f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        }
8475f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8485f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        if (!opts->no_snapshot_load || !opts->no_snapshot_save) {
8495f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            if (opts->snapshot == NULL) {
8505f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner                opts->snapshot = "default-boot";
8515f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner                D("autoconfig: -snapshot %s", opts->snapshot);
852353b3b1135563e2bcaf7797acfa35a2fe2d3a818Ot ten Thije            }
853353b3b1135563e2bcaf7797acfa35a2fe2d3a818Ot ten Thije        }
8545f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8555f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        /* We still use QEMU command-line options for the following since
8565f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        * they can change from one invokation to the next and don't really
8575f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        * correspond to the hardware configuration itself.
8585f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        */
8595f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        if (!opts->no_snapshot_load) {
8605f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            args[n++] = "-loadvm";
8615f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            args[n++] = ASTRDUP(opts->snapshot);
8625f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        }
8635f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
8645f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        if (!opts->no_snapshot_save) {
8655f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            args[n++] = "-savevm-on-exit";
8665f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner            args[n++] = ASTRDUP(opts->snapshot);
8675f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner        }
8685f64b873605baa5519211b0d47a53c93df9d4868David 'Digit' Turner
869622b8f4c760b8c4479d28430f978bad8bb9ea32cTim Baverstock        if (opts->no_snapshot_update_time) {
870bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner            args[n++] = "-snapshot-no-time-update";
871622b8f4c760b8c4479d28430f978bad8bb9ea32cTim Baverstock        }
872ae835acc2d1a8b4aaeb599add9cfc02ea5789eafOt ten Thije    }
873353b3b1135563e2bcaf7797acfa35a2fe2d3a818Ot ten Thije
8748b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (!opts->logcat || opts->logcat[0] == 0) {
8758b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        opts->logcat = getenv("ANDROID_LOG_TAGS");
8768b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (opts->logcat && opts->logcat[0] == 0)
8778b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            opts->logcat = NULL;
8788b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
8798b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
8808b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    /* we always send the kernel messages from ttyS0 to android_kmsg */
881062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner    if (opts->show_kernel) {
882062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner        args[n++] = "-show-kernel";
8838b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
8848b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
8858b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    /* XXXX: TODO: implement -shell and -logcat through qemud instead */
8868b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (!opts->shell_serial) {
8878b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#ifdef _WIN32
8888b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        opts->shell_serial = "con:";
8898b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#else
8908b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        opts->shell_serial = "stdio";
8918b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project#endif
8928b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
8938b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    else
8948b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        opts->shell = 1;
8958b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
8968b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (opts->shell || opts->logcat) {
8978b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        args[n++] = "-serial";
8988b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        args[n++] = opts->shell_serial;
8998b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        shell_serial = serial++;
9008b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
9018b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
902062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner    if (opts->radio) {
903062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner        args[n++] = "-radio";
904062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner        args[n++] = opts->radio;
9058b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
9068b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
907062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner    if (opts->gps) {
908062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner        args[n++] = "-gps";
909062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner        args[n++] = opts->gps;
9108b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
9118b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
9128b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (opts->memory) {
9138b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        char*  end;
9148b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        long   ramSize = strtol(opts->memory, &end, 0);
9158b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (ramSize < 0 || *end != 0) {
9168b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            derror( "-memory must be followed by a positive integer" );
9178b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            exit(1);
9188b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
9198b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (ramSize < 32 || ramSize > 4096) {
9208b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            derror( "physical memory size must be between 32 and 4096 MB" );
9218b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            exit(1);
9228b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
9235377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        hw->hw_ramSize = ramSize;
9248b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
9258b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (!opts->memory) {
9263bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner        int ramSize = hw->hw_ramSize;
9273bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner        if (ramSize <= 0) {
9283bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner            /* Compute the default RAM size based on the size of screen.
9293bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             * This is only used when the skin doesn't provide the ram
9303bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             * size through its hardware.ini (i.e. legacy ones) or when
9313bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             * in the full Android build system.
9323bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             */
9335377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner            int64_t pixels  = hw->hw_lcd_width * hw->hw_lcd_height;
9343bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner            /* The following thresholds are a bit liberal, but we
9353bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             * essentially want to ensure the following mappings:
9363bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             *
9373bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             *   320x480 -> 96
9383bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             *   800x600 -> 128
9393bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             *  1024x768 -> 256
9403bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             *
9413bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             * These are just simple heuristics, they could change in
9423bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             * the future.
9433bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner             */
9443bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner            if (pixels <= 250000)
9453bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner                ramSize = 96;
9463bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner            else if (pixels <= 500000)
9473bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner                ramSize = 128;
9483bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner            else
9493bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner                ramSize = 256;
9503bbc919b70c78e0be6387d06faa90743deedb4dcDavid 'Digit' Turner        }
9515377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        hw->hw_ramSize = ramSize;
9525377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner    }
9535377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner
9545377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner    D("Physical RAM size: %dMB\n", hw->hw_ramSize);
9555377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner
9565377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner    if (hw->vm_heapSize == 0) {
9575377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        /* Compute the default heap size based on the RAM size.
9585377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner         * Essentially, we want to ensure the following liberal mappings:
9595377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner         *
9605377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner         *   96MB RAM -> 16MB heap
9615377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner         *  128MB RAM -> 24MB heap
9625377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner         *  256MB RAM -> 48MB heap
9635377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner         */
9645377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        int  ramSize = hw->hw_ramSize;
9655377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        int  heapSize;
9665377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner
9675377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        if (ramSize < 100)
9685377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner            heapSize = 16;
9695377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        else if (ramSize < 192)
9705377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner            heapSize = 24;
9715377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        else
9725377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner            heapSize = 48;
9735377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner
9745377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner        hw->vm_heapSize = heapSize;
9758b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
9768b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
9778b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if (opts->trace) {
9788b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        args[n++] = "-trace";
9798b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        args[n++] = opts->trace;
9808b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        args[n++] = "-tracing";
9818b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        args[n++] = "off";
9828b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
9838b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
984b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    /* Pass boot properties to the core. */
985b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    if (opts->prop != NULL) {
986b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine        ParamList*  pl = opts->prop;
987b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine        for ( ; pl != NULL; pl = pl->next ) {
988b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine            args[n++] = "-boot-property";
989b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine            args[n++] = pl->param;
990b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine        }
991b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine    }
992b25bf2a7477595aa54181874921086d4c0071c03Vladimir Chtchetkine
993318e4f294c181df33cf2541763904565b29bcccbDavid 'Digit' Turner    /* Setup the kernel init options
994318e4f294c181df33cf2541763904565b29bcccbDavid 'Digit' Turner     */
9958b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    {
9968b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        static char  params[1024];
9978b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        char        *p = params, *end = p + sizeof(params);
9988b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
999062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner        /* Don't worry about having a leading space here, this is handled
1000062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner         * by the core later. */
1001062dd6a8b90c7c553a6a7257e9c245276b1dd969David 'Digit' Turner
1002334ab475d2f27dbf6fbf836c2d4fb86dbb02a15cJun Nakajima#ifdef TARGET_I386
1003334ab475d2f27dbf6fbf836c2d4fb86dbb02a15cJun Nakajima        p = bufprint(p, end, " androidboot.hardware=goldfish");
1004bac9add881e0b7cfa2da2b86242347c096329a4cJun Nakajima        p = bufprint(p, end, " clocksource=pit");
1005334ab475d2f27dbf6fbf836c2d4fb86dbb02a15cJun Nakajima#endif
10068b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10078b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (opts->shell || opts->logcat) {
10088b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            p = bufprint(p, end, " androidboot.console=ttyS%d", shell_serial );
10098b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
10108b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10118b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (opts->trace) {
10128b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            p = bufprint(p, end, " android.tracing=1");
10138b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
10148b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10158b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (!opts->no_jni) {
10168b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            p = bufprint(p, end, " android.checkjni=1");
10178b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
10188b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10198b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (opts->no_boot_anim) {
10208b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            p = bufprint( p, end, " android.bootanim=0" );
10218b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
10228b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10238b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (opts->logcat) {
10248b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            char*  q = bufprint(p, end, " androidboot.logcat=%s", opts->logcat);
10258b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10268b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            if (q < end) {
10278b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                /* replace any space by a comma ! */
10288b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                {
10298b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                    int  nn;
10308b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                    for (nn = 1; p[nn] != 0; nn++)
10318b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                        if (p[nn] == ' ' || p[nn] == '\t')
10328b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                            p[nn] = ',';
10338b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                    p += nn;
10348b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project                }
10358b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            }
10368b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            p = q;
10378b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
10388b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10398b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (opts->bootchart) {
10408b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            p = bufprint(p, end, " androidboot.bootchart=%s", opts->bootchart);
10418b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
10428b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10438b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        if (p >= end) {
10448b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            fprintf(stderr, "### ERROR: kernel parameters too long\n");
10458b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project            exit(1);
10468b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
10478b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
10480b0194940523fa3f318c380d0693907bd522241cDavid 'Digit' Turner        hw->kernel_parameters = strdup(params);
10498b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
10508b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
1051d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    if (opts->ports) {
1052d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = "-android-ports";
1053d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = opts->ports;
1054d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    }
1055d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine
1056d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    if (opts->port) {
1057d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = "-android-port";
1058d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = opts->port;
1059d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    }
1060d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine
1061d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    if (opts->report_console) {
1062d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = "-android-report-console";
1063d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = opts->report_console;
1064d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    }
1065d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine
1066d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    if (opts->http_proxy) {
1067d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = "-http-proxy";
1068d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine        args[n++] = opts->http_proxy;
1069d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine    }
1070d81e6d1ce722d7e561d495bbd4b137e728e25b83Vladimir Chtchetkine
107172d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet    if (!opts->charmap) {
107272d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        /* Try to find a valid charmap name */
107372d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        char* charmap = avdInfo_getCharmapFile(avd, hw->hw_keyboard_charmap);
107472d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        if (charmap != NULL) {
107572d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet            D("autoconfig: -charmap %s", charmap);
107672d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet            opts->charmap = charmap;
107772d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        }
107872d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet    }
107972d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet
108043552dc4fa64aad0c9fdb8f4c92ae7ac79406596Vladimir Chtchetkine    if (opts->charmap) {
108172d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        char charmap_name[AKEYCHARMAP_NAME_SIZE];
108272d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet
108372d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        if (!path_exists(opts->charmap)) {
108472d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet            derror("Charmap file does not exist: %s", opts->charmap);
108572d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet            exit(1);
108672d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        }
108772d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        /* We need to store the charmap name in the hardware configuration.
108872d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet         * However, the charmap file itself is only used by the UI component
108972d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet         * and doesn't need to be set to the emulation engine.
109072d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet         */
109172d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        kcm_extract_charmap_name(opts->charmap, charmap_name,
109272d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet                                 sizeof(charmap_name));
109372d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        AFREE(hw->hw_keyboard_charmap);
109472d561178e62b74923cfe3bc0faa59bcb07c57c3Xavier Ducrohet        hw->hw_keyboard_charmap = ASTRDUP(charmap_name);
109543552dc4fa64aad0c9fdb8f4c92ae7ac79406596Vladimir Chtchetkine    }
109643552dc4fa64aad0c9fdb8f4c92ae7ac79406596Vladimir Chtchetkine
1097b5365f32d7b1dcc6c3e9be7584ce8d4f68b3e7e1Vladimir Chtchetkine    if (opts->memcheck) {
1098b5365f32d7b1dcc6c3e9be7584ce8d4f68b3e7e1Vladimir Chtchetkine        args[n++] = "-android-memcheck";
1099b5365f32d7b1dcc6c3e9be7584ce8d4f68b3e7e1Vladimir Chtchetkine        args[n++] = opts->memcheck;
1100b5365f32d7b1dcc6c3e9be7584ce8d4f68b3e7e1Vladimir Chtchetkine    }
1101b5365f32d7b1dcc6c3e9be7584ce8d4f68b3e7e1Vladimir Chtchetkine
11029da935dd0c616cfd9072d11080a622320497dc9eDavid Turner    if (opts->gpu) {
11039da935dd0c616cfd9072d11080a622320497dc9eDavid Turner        const char* gpu = opts->gpu;
1104ae0d8136ce0d3c39ca80c64763e633b86b0c5453Vladimir Chtchetkine        if (!strcmp(gpu,"on") || !strcmp(gpu,"enable")) {
11059da935dd0c616cfd9072d11080a622320497dc9eDavid Turner            hw->hw_gpu_enabled = 1;
1106ae0d8136ce0d3c39ca80c64763e633b86b0c5453Vladimir Chtchetkine        } else if (!strcmp(gpu,"off") || !strcmp(gpu,"disable")) {
11079da935dd0c616cfd9072d11080a622320497dc9eDavid Turner            hw->hw_gpu_enabled = 0;
11089da935dd0c616cfd9072d11080a622320497dc9eDavid Turner        } else if (!strcmp(gpu,"auto")) {
11099da935dd0c616cfd9072d11080a622320497dc9eDavid Turner            /* Nothing to do */
11109da935dd0c616cfd9072d11080a622320497dc9eDavid Turner        } else {
11119da935dd0c616cfd9072d11080a622320497dc9eDavid Turner            derror("Invalid value for -gpu <mode> parameter: %s\n", gpu);
11129da935dd0c616cfd9072d11080a622320497dc9eDavid Turner            derror("Valid values are: on, off or auto\n");
11139da935dd0c616cfd9072d11080a622320497dc9eDavid Turner            exit(1);
11149da935dd0c616cfd9072d11080a622320497dc9eDavid Turner        }
11159da935dd0c616cfd9072d11080a622320497dc9eDavid Turner    }
11169da935dd0c616cfd9072d11080a622320497dc9eDavid Turner
11179242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine    /* Quit emulator on condition that both, gpu and snapstorage are on. This is
11189242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine     * a temporary solution preventing the emulator from crashing until GPU state
11199242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine     * can be properly saved / resored in snapshot file. */
11209242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine    if (hw->hw_gpu_enabled && opts->snapstorage && (!opts->no_snapshot_load ||
11219242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine                                                    !opts->no_snapshot_save)) {
11229242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine        derror("Snapshots and gpu are mutually exclusive at this point. Please turn one of them off, and restart the emulator.");
11239242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine        exit(1);
11249242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine    }
11259242b33d3545e6632d21c1f416794a9f5d385c45Vladimir Chtchetkine
11267485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine    /* Deal with camera emulation */
11277485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine    if (opts->webcam_list) {
11287485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        /* List connected webcameras */
11297485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        args[n++] = "-list-webcam";
11307485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine    }
11317485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine
11327485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine    if (opts->camera_back) {
11337485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        /* Validate parameter. */
11347485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        if (memcmp(opts->camera_back, "webcam", 6) &&
11357485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine            strcmp(opts->camera_back, "emulated") &&
11367485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine            strcmp(opts->camera_back, "none")) {
11377485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine            derror("Invalid value for -camera-back <mode> parameter: %s\n"
11387485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine                   "Valid values are: 'emulated', 'webcam<N>', or 'none'\n",
11397485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine                   opts->camera_back);
1140ae0d8136ce0d3c39ca80c64763e633b86b0c5453Vladimir Chtchetkine            exit(1);
1141ae0d8136ce0d3c39ca80c64763e633b86b0c5453Vladimir Chtchetkine        }
11427485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        hw->hw_camera_back = ASTRDUP(opts->camera_back);
1143ae0d8136ce0d3c39ca80c64763e633b86b0c5453Vladimir Chtchetkine    }
1144ae0d8136ce0d3c39ca80c64763e633b86b0c5453Vladimir Chtchetkine
11457485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine    if (opts->camera_front) {
11467485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        /* Validate parameter. */
11477485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        if (memcmp(opts->camera_front, "webcam", 6) &&
11487485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine            strcmp(opts->camera_front, "emulated") &&
11497485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine            strcmp(opts->camera_front, "none")) {
11507485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine            derror("Invalid value for -camera-front <mode> parameter: %s\n"
11517485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine                   "Valid values are: 'emulated', 'webcam<N>', or 'none'\n",
11527485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine                   opts->camera_front);
11537485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine            exit(1);
1154f8675c20db7625adc69800ca4ac54e72846ac9a8Vladimir Chtchetkine        }
11557485c2989d727a1d0c14a66fb75e140f885a1583Vladimir Chtchetkine        hw->hw_camera_front = ASTRDUP(opts->camera_front);
1156f8675c20db7625adc69800ca4ac54e72846ac9a8Vladimir Chtchetkine    }
1157f8675c20db7625adc69800ca4ac54e72846ac9a8Vladimir Chtchetkine
11585377c5bfde6ba62490417bb0a7d7c1be1151692eDavid 'Digit' Turner    /* physical memory is now in hw->hw_ramSize */
11598b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
116053eb66db4eba72d2e4fc951456be725e14243f25David 'Digit' Turner    hw->avd_name = ASTRDUP(avdInfo_getName(avd));
11616b8555cac04862908bf6c64565061f2c8e871ad7David 'Digit' Turner
116240beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie    /* Set up the interfaces for inter-emulator networking */
116340beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie    if (opts->shared_net_id) {
116440beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        unsigned int shared_net_id = atoi(opts->shared_net_id);
116540beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        char nic[37];
116640beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie
116740beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        args[n++] = "-net";
116840beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        args[n++] = "nic,vlan=0";
116940beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        args[n++] = "-net";
117040beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie        args[n++] = "user,vlan=0";
1171111d6f8ed6dea6e651ab450e1ea11310ff0b2857Dries Harnie
1172111d6f8ed6dea6e651ab450e1ea11310ff0b2857Dries Harnie        args[n++] = "-net";
1173111d6f8ed6dea6e651ab450e1ea11310ff0b2857Dries Harnie        snprintf(nic, sizeof nic, "nic,vlan=1,macaddr=52:54:00:12:34:%02x", shared_net_id);
1174111d6f8ed6dea6e651ab450e1ea11310ff0b2857Dries Harnie        args[n++] = strdup(nic);
1175111d6f8ed6dea6e651ab450e1ea11310ff0b2857Dries Harnie        args[n++] = "-net";
1176111d6f8ed6dea6e651ab450e1ea11310ff0b2857Dries Harnie        args[n++] = "socket,vlan=1,mcast=230.0.0.10:1234";
117740beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie    }
117840beab42ecdc4e2a79714b54c401feb0fb33b6d0Dries Harnie
11798dd31e8e10fc3ca10192368acf19d2345eeddde7Vladimir Chtchetkine    /* Setup screen emulation */
11808dd31e8e10fc3ca10192368acf19d2345eeddde7Vladimir Chtchetkine    if (opts->screen) {
1181863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine        if (strcmp(opts->screen, "touch") &&
1182863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine            strcmp(opts->screen, "multi-touch") &&
1183863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine            strcmp(opts->screen, "no-touch")) {
1184863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine
1185863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine            derror("Invalid value for -screen <mode> parameter: %s\n"
1186863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine                   "Valid values are: touch, multi-touch, or no-touch\n",
1187863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine                   opts->screen);
11888dd31e8e10fc3ca10192368acf19d2345eeddde7Vladimir Chtchetkine            exit(1);
11898dd31e8e10fc3ca10192368acf19d2345eeddde7Vladimir Chtchetkine        }
1190863d1010d9c8fa4342b1b0ea860bcfb096806accVladimir Chtchetkine        hw->hw_screen = ASTRDUP(opts->screen);
11918dd31e8e10fc3ca10192368acf19d2345eeddde7Vladimir Chtchetkine    }
11928dd31e8e10fc3ca10192368acf19d2345eeddde7Vladimir Chtchetkine
11938b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    while(argc-- > 0) {
11948b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        args[n++] = *argv++;
11958b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
11968b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    args[n] = 0;
11978b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project
11982ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner    /* If the target ABI is armeabi-v7a, we can auto-detect the cpu model
11992ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner     * as a cortex-a8, instead of the default (arm926) which only emulates
12002ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner     * an ARMv5TE CPU.
12012ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner     */
12022ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner    if (!forceArmv7 && hw->hw_cpu_model[0] == '\0')
12032ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner    {
12042ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner        char* abi = avdInfo_getTargetAbi(avd);
12052ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner        if (abi != NULL) {
12062ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner            if (!strcmp(abi, "armeabi-v7a")) {
12072ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner                forceArmv7 = 1;
12082ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner            }
12092ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner            AFREE(abi);
12102ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner        }
12112ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner    }
12122ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner
12132ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner    if (forceArmv7 != 0) {
12142ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner        AFREE(hw->hw_cpu_model);
12152ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner        hw->hw_cpu_model = ASTRDUP("cortex-a8");
12162ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner        D("Auto-config: -qemu -cpu %s", hw->hw_cpu_model);
12172ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner    }
12182ed457ee5259b236bf39701404897f4c486326e8David 'Digit' Turner
121926d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner    /* Generate a hardware-qemu.ini for this AVD. The real hardware
1220622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner     * configuration is ususally stored in several files, e.g. the AVD's
1221622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner     * config.ini plus the skin-specific hardware.ini.
1222622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner     *
122326d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner     * The new file will group all definitions and will be used to
1224622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner     * launch the core with the -android-hw <file> option.
1225622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner     */
1226622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner    {
122742074e5e184aed78dee0efb14d7376325516c070David 'Digit' Turner        const char* coreHwIniPath = avdInfo_getCoreHwIniPath(avd);
122842074e5e184aed78dee0efb14d7376325516c070David 'Digit' Turner        IniFile*    hwIni         = iniFile_newFromMemory("", NULL);
1229622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner        androidHwConfig_write(hw, hwIni);
123026d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner
123126d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner        if (filelock_create(coreHwIniPath) == NULL) {
123226d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner            /* The AVD is already in use, we still support this as an
123326d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner             * experimental feature. Use a temporary hardware-qemu.ini
123426d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner             * file though to avoid overwriting the existing one. */
123526d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner             TempFile*  tempIni = tempfile_create();
123626d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner             coreHwIniPath = tempfile_path(tempIni);
123726d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner        }
123826d415322b75784f123d39f36616b8ebd1fbb359David 'Digit' Turner
1239db450d73092add519efddcd6d55c7a0e7541ec70Vladimir Chtchetkine        /* While saving HW config, ignore valueless entries. This will not break
1240db450d73092add519efddcd6d55c7a0e7541ec70Vladimir Chtchetkine         * anything, but will significantly simplify comparing the current HW
1241db450d73092add519efddcd6d55c7a0e7541ec70Vladimir Chtchetkine         * config with the one that has been associated with a snapshot (in case
1242db450d73092add519efddcd6d55c7a0e7541ec70Vladimir Chtchetkine         * VM starts from a snapshot for this instance of emulator). */
1243db450d73092add519efddcd6d55c7a0e7541ec70Vladimir Chtchetkine        if (iniFile_saveToFileClean(hwIni, coreHwIniPath) < 0) {
124442074e5e184aed78dee0efb14d7376325516c070David 'Digit' Turner            derror("Could not write hardware.ini to %s: %s", coreHwIniPath, strerror(errno));
1245622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner            exit(2);
1246622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner        }
1247622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner        args[n++] = "-android-hw";
124842074e5e184aed78dee0efb14d7376325516c070David 'Digit' Turner        args[n++] = strdup(coreHwIniPath);
12490a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner
12500a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner        /* In verbose mode, dump the file's content */
12510a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner        if (VERBOSE_CHECK(init)) {
12520a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner            FILE* file = fopen(coreHwIniPath, "rt");
12530a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner            if (file == NULL) {
12540a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                derror("Could not open hardware configuration file: %s\n",
12550a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                       coreHwIniPath);
12560a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner            } else {
12570a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                LineInput* input = lineInput_newFromStdFile(file);
12580a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                const char* line;
12590a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                printf("Content of hardware configuration file:\n");
12600a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                while ((line = lineInput_getLine(input)) !=  NULL) {
12610a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                    printf("  %s\n", line);
12620a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                }
12630a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                printf(".\n");
12640a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                lineInput_free(input);
12650a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner                fclose(file);
12660a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner            }
12670a879bf9ba318562e41a1bd4a6f9547f124a9831David 'Digit' Turner        }
1268622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner    }
1269622f1530c8a6badfbcaf8c59976348678fbe248bDavid 'Digit' Turner
12708b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    if(VERBOSE_CHECK(init)) {
12718b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        int i;
12723336176fc898915b7b5544f3a7c60ec2794507c3David 'Digit' Turner        printf("QEMU options list:\n");
12738b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        for(i = 0; i < n; i++) {
12743336176fc898915b7b5544f3a7c60ec2794507c3David 'Digit' Turner            printf("emulator: argv[%02d] = \"%s\"\n", i, args[i]);
12758b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project        }
12763336176fc898915b7b5544f3a7c60ec2794507c3David 'Digit' Turner        /* Dump final command-line option to make debugging the core easier */
12773336176fc898915b7b5544f3a7c60ec2794507c3David 'Digit' Turner        printf("Concatenated QEMU options:\n");
12783336176fc898915b7b5544f3a7c60ec2794507c3David 'Digit' Turner        for (i = 0; i < n; i++) {
127926722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner            /* To make it easier to copy-paste the output to a command-line,
128026722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner             * quote anything that contains spaces.
128126722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner             */
128226722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner            if (strchr(args[i], ' ') != NULL) {
128326722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner                printf(" '%s'", args[i]);
128426722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner            } else {
128526722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner                printf(" %s", args[i]);
128626722dde31c3467cd31a078662810927eec05de5David 'Digit' Turner            }
12873336176fc898915b7b5544f3a7c60ec2794507c3David 'Digit' Turner        }
12883336176fc898915b7b5544f3a7c60ec2794507c3David 'Digit' Turner        printf("\n");
12898b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    }
129074d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner
129174d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner    /* Setup SDL UI just before calling the code */
129274d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner    init_sdl_ui(skinConfig, skinPath, opts);
129374d7acec6643694132a127feb5ccadda7ea793d6David 'Digit' Turner
1294bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner    if (attach_ui_to_core(opts) < 0) {
1295bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner        derror("Can't attach to core!");
1296bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner        exit(1);
1297bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner    }
1298bdb6f2dd35a4c749186e665d55d7b76375d7e71dDavid 'Digit' Turner
12998b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project    return qemu_main(n, args);
13008b23a6c7e1aee255004dd19098d4c2462b61b849The Android Open Source Project}
1301