Annotation of previous/src/main.c, revision 1.1.1.6

1.1       root        1: /*
                      2:   Hatari - main.c
                      3: 
                      4:   This file is distributed under the GNU Public License, version 2 or at
                      5:   your option any later version. Read the file gpl.txt for details.
                      6: 
                      7:   Main initialization and event handling routines.
                      8: */
                      9: const char Main_fileid[] = "Hatari main.c : " __DATE__ " " __TIME__;
                     10: 
                     11: #include <time.h>
1.1.1.2   root       12: #include <errno.h>
1.1.1.6 ! root       13: #include <signal.h>
1.1       root       14: 
                     15: #include "main.h"
                     16: #include "configuration.h"
                     17: #include "control.h"
                     18: #include "options.h"
                     19: #include "dialog.h"
                     20: #include "ioMem.h"
1.1.1.2   root       21: #include "keymap.h"
1.1       root       22: #include "log.h"
                     23: #include "m68000.h"
                     24: #include "paths.h"
                     25: #include "reset.h"
                     26: #include "screen.h"
                     27: #include "sdlgui.h"
                     28: #include "shortcut.h"
1.1.1.6 ! root       29: #include "snd.h"
1.1       root       30: #include "statusbar.h"
                     31: #include "nextMemory.h"
                     32: #include "str.h"
                     33: #include "video.h"
1.1.1.5   root       34: #include "audio.h"
1.1       root       35: #include "debugui.h"
1.1.1.4   root       36: #include "file.h"
1.1.1.5   root       37: #include "dsp.h"
1.1.1.6 ! root       38: #include "host.h"
        !            39: #include "dimension.h"
1.1.1.2   root       40: 
1.1       root       41: #include "hatari-glue.h"
                     42: 
1.1.1.2   root       43: #if HAVE_GETTIMEOFDAY
                     44: #include <sys/time.h>
                     45: #endif
1.1       root       46: 
1.1.1.4   root       47: int nFrameSkips;
1.1       root       48: 
                     49: bool bQuitProgram = false;                /* Flag to quit program cleanly */
                     50: 
                     51: static bool bEmulationActive = true;      /* Run emulation when started */
                     52: static bool bAccurateDelays;              /* Host system has an accurate SDL_Delay()? */
                     53: static bool bIgnoreNextMouseMotion = false;  /* Next mouse motion will be ignored (needed after SDL_WarpMouse) */
                     54: 
1.1.1.6 ! root       55: volatile int mainPauseEmulation;
1.1       root       56: 
1.1.1.6 ! root       57: typedef const char* (*report_func)(double realTime, double hostTime);
1.1.1.2   root       58: 
1.1.1.6 ! root       59: typedef struct {
        !            60:     const char*       label;
        !            61:     const report_func report;
        !            62: } report_t;
        !            63: 
        !            64: static double lastRT;
        !            65: static Uint64 lastCycles;
        !            66: static double speedFactor;
        !            67: static char   speedMsg[32];
        !            68: 
        !            69: void Main_Speed(double realTime, double hostTime) {
        !            70:     double dRT = realTime - lastRT;
        !            71:     speedFactor = nCyclesMainCounter - lastCycles;
        !            72:     speedFactor /= ConfigureParams.System.nCpuFreq;
        !            73:     speedFactor /= 1000 * 1000;
        !            74:     speedFactor /= dRT;
        !            75:     lastRT     = realTime;
        !            76:     lastCycles = nCyclesMainCounter;
        !            77: }
        !            78: 
        !            79: void Main_SpeedReset(void) {
        !            80:     double realTime, hostTime;
        !            81:     host_time(&realTime, &hostTime);
        !            82:     lastRT     = realTime;
        !            83:     lastCycles = nCyclesMainCounter;
        !            84: }
        !            85: 
        !            86: const char* Main_SpeedMsg() {
        !            87:     speedMsg[0] = 0;
        !            88:     if(speedFactor > 0) {
        !            89:         if(ConfigureParams.System.bRealtime) {
        !            90:             sprintf(speedMsg, "%dMHz/", (int)(ConfigureParams.System.nCpuFreq * speedFactor + 0.5));
        !            91:         } else {
        !            92:             if ((speedFactor < 0.9) || (speedFactor > 1.1))
        !            93:                 sprintf(speedMsg, "%.1fx%dMHz/", speedFactor, ConfigureParams.System.nCpuFreq);
        !            94:             else
        !            95:                 sprintf(speedMsg, "%dMHz/",                   ConfigureParams.System.nCpuFreq);
        !            96:         }
        !            97:     }
        !            98:     return speedMsg;
1.1.1.2   root       99: }
                    100: 
1.1.1.6 ! root      101: #if ENABLE_TESTING
        !           102: static const report_t reports[] = {
        !           103:     {"ND",    nd_reports},
        !           104:     {"Host",  host_report},
        !           105: };
1.1.1.2   root      106: #endif
                    107: 
1.1       root      108: /*-----------------------------------------------------------------------*/
                    109: /**
                    110:  * Pause emulation, stop sound.  'visualize' should be set true,
                    111:  * unless unpause will be called immediately afterwards.
                    112:  * 
                    113:  * @return true if paused now, false if was already paused
                    114:  */
1.1.1.6 ! root      115: bool Main_PauseEmulation(bool visualize) {
1.1       root      116:        if ( !bEmulationActive )
                    117:                return false;
                    118: 
                    119:        bEmulationActive = false;
1.1.1.6 ! root      120:     host_pause_time(!(bEmulationActive));
        !           121:     Screen_Pause(true);
        !           122:     Sound_Pause(true);
        !           123:     if (ConfigureParams.Dimension.bEnabled) {
        !           124:         dimension_pause(true);
        !           125:     }
        !           126:     
        !           127:        if (visualize) {
1.1       root      128:                Statusbar_AddMessage("Emulation paused", 100);
                    129:                /* make sure msg gets shown */
                    130:                Statusbar_Update(sdlscrn);
                    131: 
1.1.1.5   root      132:                if (bGrabMouse && !bInFullScreen) {
1.1       root      133:                        /* Un-grab mouse pointer in windowed mode */
1.1.1.5   root      134:                        SDL_SetRelativeMouseMode(SDL_FALSE);
                    135:             SDL_SetWindowGrab(sdlWindow, SDL_FALSE);
                    136:         }
1.1       root      137:        }
                    138:        return true;
                    139: }
                    140: 
                    141: /*-----------------------------------------------------------------------*/
                    142: /**
                    143:  * Start/continue emulation
                    144:  * 
                    145:  * @return true if continued, false if was already running
                    146:  */
1.1.1.6 ! root      147: bool Main_UnPauseEmulation(void) {
1.1       root      148:        if ( bEmulationActive )
                    149:                return false;
                    150: 
                    151:        bEmulationActive = true;
1.1.1.6 ! root      152:     host_pause_time(!(bEmulationActive));
        !           153:     Screen_Pause(false);
        !           154:     Sound_Pause(false);
        !           155:     if (ConfigureParams.Dimension.bEnabled) {
        !           156:         dimension_pause(false);
        !           157:     }
1.1       root      158: 
1.1.1.5   root      159:        if (bGrabMouse) {
1.1       root      160:                /* Grab mouse pointer again */
1.1.1.5   root      161:                SDL_SetRelativeMouseMode(SDL_TRUE);
                    162:         SDL_SetWindowGrab(sdlWindow, SDL_TRUE);
                    163:     }
1.1       root      164:        return true;
                    165: }
                    166: 
                    167: /*-----------------------------------------------------------------------*/
                    168: /**
                    169:  * Optionally ask user whether to quit and set bQuitProgram accordingly
                    170:  */
1.1.1.6 ! root      171: void Main_RequestQuit(void) {
        !           172:     if (ConfigureParams.Log.bConfirmQuit) {
1.1       root      173:                bQuitProgram = false;   /* if set true, dialog exits */
                    174:                bQuitProgram = DlgAlert_Query("All unsaved data will be lost.\nDo you really want to quit?");
                    175:        }
1.1.1.6 ! root      176:        else {
1.1       root      177:                bQuitProgram = true;
                    178:        }
                    179: 
1.1.1.6 ! root      180:        if (bQuitProgram) {
1.1       root      181:                /* Assure that CPU core shuts down */
                    182:                M68000_SetSpecial(SPCFLAG_BRK);
                    183:        }
                    184: }
                    185: 
                    186: /*-----------------------------------------------------------------------*/
                    187: /**
                    188:  * Since SDL_Delay and friends are very inaccurate on some systems, we have
                    189:  * to check if we can rely on this delay function.
                    190:  */
1.1.1.6 ! root      191: static void Main_CheckForAccurateDelays(void) {
1.1       root      192:        int nStartTicks, nEndTicks;
                    193: 
                    194:        /* Force a task switch now, so we have a longer timeslice afterwards */
                    195:        SDL_Delay(10);
                    196: 
                    197:        nStartTicks = SDL_GetTicks();
                    198:        SDL_Delay(1);
                    199:        nEndTicks = SDL_GetTicks();
                    200: 
                    201:        /* If the delay took longer than 10ms, we are on an inaccurate system! */
                    202:        bAccurateDelays = ((nEndTicks - nStartTicks) < 9);
                    203: 
                    204:        if (bAccurateDelays)
                    205:                Log_Printf(LOG_WARN, "Host system has accurate delays. (%d)\n", nEndTicks - nStartTicks);
                    206:        else
                    207:                Log_Printf(LOG_WARN, "Host system does not have accurate delays. (%d)\n", nEndTicks - nStartTicks);
                    208: }
                    209: 
                    210: 
                    211: /* ----------------------------------------------------------------------- */
                    212: /**
                    213:  * Set mouse pointer to new coordinates and set flag to ignore the mouse event
                    214:  * that is generated by SDL_WarpMouse().
                    215:  */
1.1.1.6 ! root      216: void Main_WarpMouse(int x, int y) {
1.1.1.5   root      217:     SDL_WarpMouseInWindow(sdlWindow, x, y); /* Set mouse pointer to new position */
                    218:        bIgnoreNextMouseMotion = true;          /* Ignore mouse motion event from SDL_WarpMouse */
1.1       root      219: }
                    220: 
                    221: 
                    222: /* ----------------------------------------------------------------------- */
                    223: /**
                    224:  * Handle mouse motion event.
                    225:  */
1.1.1.5   root      226: SDL_Event mymouse[100];
1.1.1.6 ! root      227: static void Main_HandleMouseMotion(SDL_Event *pEvent) {
1.1       root      228:        int dx, dy;
1.1.1.5   root      229:        int i,nb;
1.1       root      230: 
                    231:        dx = pEvent->motion.xrel;
                    232:        dy = pEvent->motion.yrel;
                    233: 
1.1.1.5   root      234:        /* get all mouse event to clean the queue and sum them */
                    235:        nb=SDL_PeepEvents(&mymouse[0], 100, SDL_GETEVENT, SDL_MOUSEMOTION, SDL_MOUSEMOTION);
                    236: 
                    237:        for (i=0;i<nb;i++) {
1.1.1.6 ! root      238:         dx += mymouse[i].motion.xrel;
        !           239:         dy += mymouse[i].motion.yrel;
1.1       root      240:        }
                    241: 
1.1.1.5   root      242:        if (bGrabMouse) {
                    243:        Keymap_MouseMove(dx,dy,ConfigureParams.Mouse.fLinSpeedLocked,ConfigureParams.Mouse.fExpSpeedLocked);
                    244:        } else {
                    245:        Keymap_MouseMove(dx,dy,ConfigureParams.Mouse.fLinSpeedNormal,ConfigureParams.Mouse.fLinSpeedNormal);
                    246:        }
1.1       root      247: }
                    248: 
1.1.1.6 ! root      249: static int statusBarUpdate;
1.1       root      250: 
                    251: /* ----------------------------------------------------------------------- */
                    252: /**
                    253:  * SDL message handler.
1.1.1.6 ! root      254:  * Here we process the SDL events (keyboard, mouse, ...)
1.1       root      255:  */
1.1.1.6 ! root      256: void Main_EventHandler(void) {
        !           257:     bool bContinueProcessing;
        !           258:     SDL_Event event;
        !           259:     int events;
        !           260:     int remotepause;
        !           261:     
        !           262:     if(++statusBarUpdate > 400) {
        !           263:         double vt;
        !           264:         double rt;
        !           265:         host_time(&rt, &vt);
        !           266: #if ENABLE_TESTING
        !           267:         fprintf(stderr, "[reports]");
        !           268:         for(int i = 0; i < sizeof(reports)/sizeof(report_t); i++) {
        !           269:             const char* msg = reports[i].report(rt, vt);
        !           270:             if(msg[0]) fprintf(stderr, " %s:%s", reports[i].label, msg);
        !           271:         }
        !           272:         fprintf(stderr, "\n");
        !           273: #else
        !           274:         Main_Speed(rt, vt);
        !           275: #endif
        !           276:         Statusbar_UpdateInfo();
        !           277:         statusBarUpdate = 0;
        !           278:     }
        !           279:     
        !           280:     do {
        !           281:         bContinueProcessing = false;
        !           282:         
        !           283:         /* check remote process control from different thread (e.g. i860) */
        !           284:         switch(mainPauseEmulation) {
        !           285:             case PAUSE_EMULATION:
        !           286:                 mainPauseEmulation = PAUSE_NONE;
        !           287:                 Main_PauseEmulation(true);
        !           288:                 break;
        !           289:             case UNPAUSE_EMULATION:
        !           290:                 mainPauseEmulation = PAUSE_NONE;
        !           291:                 Main_UnPauseEmulation();
        !           292:                 break;
        !           293:         }
        !           294:         
        !           295:         /* check remote process control */
        !           296:         remotepause = Control_CheckUpdates();
        !           297:         
        !           298:         if ( bEmulationActive || remotepause ) {
        !           299:             double time_offset = host_real_time_offset() * 1000;
        !           300:             if(time_offset > 10)
        !           301:                 events = SDL_WaitEventTimeout(&event, time_offset);
        !           302:             else
        !           303:                 events = SDL_PollEvent(&event);
        !           304:         }
        !           305:         else {
        !           306:             ShortCut_ActKey();
        !           307:             /* last (shortcut) event activated emulation? */
        !           308:             if ( bEmulationActive )
        !           309:                 break;
        !           310:             events = SDL_WaitEvent(&event);
        !           311:         }
        !           312:         if (!events) {
        !           313:             /* no events -> if emulation is active or
        !           314:              * user is quitting -> return from function.
        !           315:              */
        !           316:             continue;
        !           317:         }
        !           318:         switch (event.type) {
        !           319:             case SDL_WINDOWEVENT:
        !           320:                 if(event.window.event == SDL_WINDOWEVENT_CLOSE) {
        !           321:                     SDL_WaitEventTimeout(&event, 100); // grab SDL_Quit if pending
1.1.1.5   root      322:                     Main_RequestQuit();
1.1.1.6 ! root      323:                 }
        !           324:                 continue;
        !           325: 
        !           326:             case SDL_QUIT:
        !           327:                 Main_RequestQuit();
1.1.1.5   root      328:                 break;
                    329:                 
1.1.1.6 ! root      330:             case SDL_MOUSEMOTION:               /* Read/Update internal mouse position */
        !           331:                 Main_HandleMouseMotion(&event);
        !           332:                 bContinueProcessing = false;
        !           333:                 break;
1.1.1.5   root      334:                 
1.1.1.6 ! root      335:             case SDL_MOUSEBUTTONDOWN:
        !           336:                 if (event.button.button == SDL_BUTTON_LEFT) {
        !           337:                     if (ConfigureParams.Mouse.bEnableAutoGrab && !bGrabMouse) {
        !           338:                         bGrabMouse = true;        /* Toggle flag */
        !           339:                         
        !           340:                         /* If we are in windowed mode, toggle the mouse cursor mode now: */
        !           341:                         if (!bInFullScreen)
        !           342:                         {
        !           343:                             SDL_SetRelativeMouseMode(SDL_TRUE);
        !           344:                             SDL_SetWindowGrab(sdlWindow, SDL_TRUE);
        !           345:                             Main_SetTitle(MOUSE_LOCK_MSG);
        !           346:                         }
        !           347:                     }
        !           348:                     
        !           349:                     Keymap_MouseDown(true);
        !           350:                 }
        !           351:                 else if (event.button.button == SDL_BUTTON_RIGHT)
        !           352:                 {
        !           353:                     Keymap_MouseDown(false);
        !           354:                 }
        !           355:                 break;
        !           356:                 
        !           357:             case SDL_MOUSEBUTTONUP:
        !           358:                 if (event.button.button == SDL_BUTTON_LEFT) {
        !           359:                     Keymap_MouseUp(true);
        !           360:                 }
        !           361:                 else if (event.button.button == SDL_BUTTON_RIGHT)
        !           362:                 {
        !           363:                     Keymap_MouseUp(false);
        !           364:                 }
        !           365:                 break;
        !           366:                 
        !           367:             case SDL_MOUSEWHEEL:
        !           368:                 Keymap_MouseWheel(&event.wheel);
        !           369:                 break;
        !           370:                 
        !           371:             case SDL_KEYDOWN:
        !           372:                 if (event.key.repeat)
        !           373:                     break;
        !           374:                 
        !           375:                 Keymap_KeyDown(&event.key.keysym);
        !           376:                 break;
        !           377:                 
        !           378:             case SDL_KEYUP:
        !           379:                 Keymap_KeyUp(&event.key.keysym);
        !           380:                 break;
        !           381:                 
        !           382:                 
        !           383:             default:
        !           384:                 /* don't let unknown events delay event processing */
        !           385:                 bContinueProcessing = true;
        !           386:                 break;
        !           387:         }
        !           388:     } while (bContinueProcessing || !(bEmulationActive || bQuitProgram));
1.1       root      389: }
                    390: 
                    391: 
1.1.1.6 ! root      392: void Main_EventHandlerInterrupt() {
        !           393:     CycInt_AcknowledgeInterrupt();
        !           394:     Main_EventHandler();
        !           395:     CycInt_AddRelativeInterruptUs((1000*1000)/200, 0, INTERRUPT_EVENT_LOOP); // poll events with 200 Hz
        !           396: }
        !           397: 
1.1       root      398: /*-----------------------------------------------------------------------*/
                    399: /**
1.1.1.2   root      400:  * Set Hatari window title. Use NULL for default
                    401:  */
1.1.1.6 ! root      402: void Main_SetTitle(const char *title) {
1.1.1.5   root      403:     if (title)
                    404:         SDL_SetWindowTitle(sdlWindow, title);
                    405:     else
                    406:         SDL_SetWindowTitle(sdlWindow, PROG_NAME);
1.1.1.2   root      407: }
                    408: 
                    409: /*-----------------------------------------------------------------------*/
                    410: /**
1.1       root      411:  * Initialise emulation
                    412:  */
1.1.1.6 ! root      413: static void Main_Init(void) {
1.1       root      414:        /* Open debug log file */
1.1.1.6 ! root      415:        if (!Log_Init()) {
1.1       root      416:                fprintf(stderr, "Logging/tracing initialization failed\n");
                    417:                exit(-1);
                    418:        }
                    419:        Log_Printf(LOG_INFO, PROG_NAME ", compiled on:  " __DATE__ ", " __TIME__ "\n");
                    420: 
                    421:        /* Init SDL's video subsystem. Note: Audio and joystick subsystems
                    422:           will be initialized later (failures there are not fatal). */
1.1.1.6 ! root      423:        if (SDL_Init(SDL_INIT_VIDEO | SDL_INIT_TIMER | Opt_GetNoParachuteFlag()) < 0)
1.1       root      424:        {
                    425:                fprintf(stderr, "Could not initialize the SDL library:\n %s\n", SDL_GetError() );
                    426:                exit(-1);
                    427:        }
                    428:        SDLGui_Init();
                    429:        Screen_Init();
1.1.1.2   root      430:        Main_SetTitle(NULL);
1.1.1.5   root      431:        DSP_Init();
1.1       root      432:        M68000_Init();                /* Init CPU emulation */
1.1.1.3   root      433:        Keymap_Init();
1.1.1.2   root      434: 
                    435:     /* call menu at startup */
1.1.1.6 ! root      436:     if (!File_Exists(sConfigFileName) || ConfigureParams.ConfigDialog.bShowConfigDialogAtStartup) {
1.1.1.4   root      437:         Dialog_DoProperty();
1.1.1.6 ! root      438:         if (bQuitProgram) {
        !           439:             SDL_Quit();
        !           440:             exit(-2);
        !           441:         }
        !           442:     }
        !           443: 
        !           444:     Dialog_CheckFiles();
1.1.1.4   root      445:     
1.1.1.6 ! root      446:     if (bQuitProgram) {
1.1.1.4   root      447:         SDL_Quit();
                    448:         exit(-2);
                    449:     }
                    450:     
                    451:     Reset_Cold();
                    452:     
1.1       root      453:        IoMem_Init();
                    454:        
1.1.1.6 ! root      455:     /* Start EventHandler */
        !           456:     CycInt_AddRelativeInterruptUs(500*1000, 0, INTERRUPT_EVENT_LOOP);
        !           457:     
1.1       root      458:        /* done as last, needs CPU & DSP running... */
                    459:        DebugUI_Init();
                    460: }
                    461: 
                    462: 
                    463: /*-----------------------------------------------------------------------*/
                    464: /**
                    465:  * Un-Initialise emulation
                    466:  */
1.1.1.6 ! root      467: static void Main_UnInit(void) {
1.1       root      468:        Screen_ReturnFromFullScreen();
                    469:        IoMem_UnInit();
                    470:        SDLGui_UnInit();
                    471:        Screen_UnInit();
                    472:        Exit680x0();
                    473: 
                    474:        /* SDL uninit: */
                    475:        SDL_Quit();
                    476: 
                    477:        /* Close debug log file */
                    478:        Log_UnInit();
                    479: }
                    480: 
                    481: 
                    482: /*-----------------------------------------------------------------------*/
                    483: /**
                    484:  * Load initial configuration file(s)
                    485:  */
1.1.1.6 ! root      486: static void Main_LoadInitialConfig(void) {
1.1       root      487:        char *psGlobalConfig;
                    488: 
                    489:        psGlobalConfig = malloc(FILENAME_MAX);
                    490:        if (psGlobalConfig)
                    491:        {
                    492: #if defined(__AMIGAOS4__)
                    493:                strncpy(psGlobalConfig, CONFDIR"previous.cfg", FILENAME_MAX);
                    494: #else
                    495:                snprintf(psGlobalConfig, FILENAME_MAX, CONFDIR"%cprevious.cfg", PATHSEP);
                    496: #endif
                    497:                /* Try to load the global configuration file */
                    498:                Configuration_Load(psGlobalConfig);
                    499: 
                    500:                free(psGlobalConfig);
                    501:        }
                    502: 
                    503:        /* Now try the users configuration file */
                    504:        Configuration_Load(NULL);
                    505: }
                    506: 
                    507: /*-----------------------------------------------------------------------*/
                    508: /**
                    509:  * Set TOS etc information and initial help message
                    510:  */
1.1.1.6 ! root      511: static void Main_StatusbarSetup(void) {
1.1       root      512:        const char *name = NULL;
1.1.1.5   root      513:        SDL_Keycode key;
1.1       root      514: 
                    515:        key = ConfigureParams.Shortcut.withoutModifier[SHORTCUT_OPTIONS];
                    516:        if (!key)
                    517:                key = ConfigureParams.Shortcut.withModifier[SHORTCUT_OPTIONS];
                    518:        if (key)
                    519:                name = SDL_GetKeyName(key);
                    520:        if (name)
                    521:        {
                    522:                char message[24], *keyname;
                    523: #ifdef _MUDFLAP
                    524:                __mf_register(name, 32, __MF_TYPE_GUESS, "SDL keyname");
                    525: #endif
                    526:                keyname = Str_ToUpper(strdup(name));
                    527:                snprintf(message, sizeof(message), "Press %s for Options", keyname);
                    528:                free(keyname);
                    529: 
                    530:                Statusbar_AddMessage(message, 6000);
                    531:        }
                    532:        /* update information loaded by Main_Init() */
                    533:        Statusbar_UpdateInfo();
                    534: }
                    535: 
1.1.1.6 ! root      536: #ifdef WIN32
        !           537:        extern void Win_OpenCon(void);
        !           538: #endif
        !           539: 
        !           540: /*-----------------------------------------------------------------------*/
        !           541: /**
        !           542:  * Set signal handlers to catch signals
        !           543:  */
        !           544: static void Main_SetSignalHandlers(void) {
        !           545: #ifndef _WIN32
        !           546:     signal(SIGPIPE, SIG_IGN);
        !           547: #endif
        !           548:     signal(SIGFPE, SIG_IGN);
        !           549: }
        !           550: 
        !           551: 
1.1       root      552: /*-----------------------------------------------------------------------*/
                    553: /**
                    554:  * Main
                    555:  * 
                    556:  * Note: 'argv' cannot be declared const, MinGW would then fail to link.
                    557:  */
1.1.1.6 ! root      558: int main(int argc, char *argv[]) {
1.1       root      559:        /* Generate random seed */
                    560:        srand(time(NULL));
1.1.1.6 ! root      561:     
        !           562:     /* Set signal handlers */
        !           563:     Main_SetSignalHandlers();
1.1       root      564: 
                    565:        /* Initialize directory strings */
                    566:        Paths_Init(argv[0]);
                    567: 
                    568:        /* Set default configuration values: */
                    569:        Configuration_SetDefault();
                    570: 
                    571:        /* Now load the values from the configuration file */
                    572:        Main_LoadInitialConfig();
1.1.1.5   root      573:     
                    574: #if 0 /* FIXME: This sometimes causes exits when starting from application bundles */
1.1       root      575:        /* Check for any passed parameters */
1.1.1.2   root      576:        if (!Opt_ParseParameters(argc, (const char * const *)argv))
1.1       root      577:        {
                    578:                return 1;
                    579:        }
1.1.1.5   root      580: #endif
1.1       root      581:        /* monitor type option might require "reset" -> true */
                    582:        Configuration_Apply(true);
                    583: 
                    584: #ifdef WIN32
                    585:        Win_OpenCon();
                    586: #endif
                    587: 
                    588:        /* Needed on maemo but useful also with normal X11 window managers
                    589:         * for window grouping when you have multiple Hatari SDL windows open
                    590:         */
                    591: #if HAVE_SETENV
                    592:        setenv("SDL_VIDEO_X11_WMCLASS", "previous", 1);
                    593: #endif
                    594: 
                    595:        /* Init emulator system */
                    596:        Main_Init();
                    597: 
                    598:        /* Set initial Statusbar information */
                    599:        Main_StatusbarSetup();
                    600:        
                    601:        /* Check if SDL_Delay is accurate */
                    602:        Main_CheckForAccurateDelays();
                    603: 
                    604: 
                    605:        /* Run emulation */
                    606:        Main_UnPauseEmulation();
                    607:        M68000_Start();                 /* Start emulation */
                    608: 
                    609:        /* Un-init emulation system */
                    610:        Main_UnInit();
                    611: 
                    612:        return 0;
                    613: }

unix.superglobalmegacorp.com

This archive runs on limited infrastructure. Preserving old code on modern bandwidth. Automated agents are requested to crawl responsibly.