- static int gp2x_old_clock = -1, EmuOpt_old = 0, pal_old = 0;\r
- static int gp2x_old_gamma = 100;\r
- char fpsbuff[24]; // fps count c string\r
- struct timeval tval; // timing\r
- int pframes_done, pframes_shown, pthissec; // "period" frames, used for sync\r
- int frames_done, frames_shown, thissec; // actual frames\r
- int oldmodes = 0, target_fps, target_frametime, lim_time, vsync_offset, i;\r
- char *notice = 0;\r
-\r
- printf("entered emu_Loop()\n");\r
-\r
- if ((EmuOpt_old ^ currentConfig.EmuOpt) & EOPT_RAM_TIMINGS) {\r
- if (currentConfig.EmuOpt & EOPT_RAM_TIMINGS)\r
- set_ram_timings();\r
- else\r
- unset_ram_timings();\r
- }\r
-\r
- if (gp2x_old_clock < 0)\r
- gp2x_old_clock = default_cpu_clock;\r
- if (gp2x_old_clock != currentConfig.CPUclock) {\r
- printf("changing clock to %i...", currentConfig.CPUclock); fflush(stdout);\r
- gp2x_set_cpuclk(currentConfig.CPUclock);\r
- gp2x_old_clock = currentConfig.CPUclock;\r
- printf(" done\n");\r
- }\r
-\r
- if (gp2x_old_gamma != currentConfig.gamma || (EmuOpt_old&0x1000) != (currentConfig.EmuOpt&0x1000)) {\r
- set_lcd_gamma(currentConfig.gamma, !!(currentConfig.EmuOpt&0x1000));\r
- gp2x_old_gamma = currentConfig.gamma;\r
- printf("updated gamma to %i, A_SN's curve: %i\n", currentConfig.gamma, !!(currentConfig.EmuOpt&0x1000));\r
- }\r
-\r
- if (((EmuOpt_old ^ currentConfig.EmuOpt) & EOPT_PSYNC) || Pico.m.pal != pal_old) {\r
- if (currentConfig.EmuOpt & EOPT_PSYNC)\r
- set_lcd_custom_rate(Pico.m.pal);\r
- else\r
- unset_lcd_custom_rate();\r
- }\r
-\r
- if ((EmuOpt_old ^ currentConfig.EmuOpt) & EOPT_MMUHACK)\r
- gp2x_make_fb_bufferable(currentConfig.EmuOpt & EOPT_MMUHACK);\r
-\r
- EmuOpt_old = currentConfig.EmuOpt;\r
- pal_old = Pico.m.pal;\r
- fpsbuff[0] = 0;\r
-\r
- // make sure we are in correct mode\r
- vidResetMode();\r
- scaling_update();\r
- Pico.m.dirtyPal = 1;\r
- oldmodes = ((Pico.video.reg[12]&1)<<2) ^ 0xc;\r
-\r
- // pal/ntsc might have changed, reset related stuff\r
- target_fps = Pico.m.pal ? 50 : 60;\r
- target_frametime = 1000000/target_fps;\r
- reset_timing = 1;\r
-\r
- pemu_sound_start();\r
-\r
- // prepare CD buffer\r
- if (PicoAHW & PAHW_MCD) PicoCDBufferInit();\r
-\r
- // calc vsync offset to sync timing code with vsync\r
- if (currentConfig.EmuOpt & EOPT_PSYNC) {\r
- gettimeofday(&tval, 0);\r
- gp2x_video_wait_vsync();\r
- gettimeofday(&tval, 0);\r
- vsync_offset = tval.tv_usec;\r
- while (vsync_offset >= target_frametime)\r
- vsync_offset -= target_frametime;\r
- if (!vsync_offset) vsync_offset++;\r
- printf("vsync_offset: %i\n", vsync_offset);\r
- } else\r
- vsync_offset = 0;\r
-\r
- frames_done = frames_shown = thissec =\r
- pframes_done = pframes_shown = pthissec = 0;\r
-\r
- // loop\r
- while (engineState == PGS_Running)\r
- {\r
- int modes;\r
-\r
- gettimeofday(&tval, 0);\r
- if (reset_timing) {\r
- reset_timing = 0;\r
- pthissec = tval.tv_sec;\r
- pframes_shown = pframes_done = tval.tv_usec/target_frametime;\r
- }\r
-\r
- // show notice message?\r
- if (noticeMsgTime.tv_sec)\r
- {\r
- static int noticeMsgSum;\r
- if((tval.tv_sec*1000000+tval.tv_usec) - (noticeMsgTime.tv_sec*1000000+noticeMsgTime.tv_usec) > 2000000) { // > 2.0 sec\r
- noticeMsgTime.tv_sec = noticeMsgTime.tv_usec = 0;\r
- clearArea(0);\r
- notice = 0;\r
- } else {\r
- int sum = noticeMsg[0]+noticeMsg[1]+noticeMsg[2];\r
- if (sum != noticeMsgSum) { clearArea(0); noticeMsgSum = sum; }\r
- notice = noticeMsg;\r
- }\r
- }\r
-\r
- // check for mode changes\r
- modes = ((Pico.video.reg[12]&1)<<2)|(Pico.video.reg[1]&8);\r
- if (modes != oldmodes)\r
- {\r
- int scalex = 320;\r
- osd_fps_x = OSD_FPS_X;\r
- if (!(modes & 4) && (PicoOpt & POPT_DIS_32C_BORDER)) {\r
- scalex = 256;\r
- osd_fps_x = OSD_FPS_X - 64;\r
- }\r
- /* want vertical scaling and game is not in 240 line mode */\r
- if (currentConfig.scaling == EOPT_SCALE_HW_HV && !(modes&8))\r
- gp2x_video_RGB_setscaling(8, scalex, 224);\r
- else gp2x_video_RGB_setscaling(0, scalex, 240);\r
- oldmodes = modes;\r
- clearArea(1);\r
- }\r
-\r
- // second changed?\r
- if (thissec != tval.tv_sec)\r
- {\r
-#ifdef BENCHMARK\r
- static int bench = 0, bench_fps = 0, bench_fps_s = 0, bfp = 0, bf[4];\r
- if (++bench == 10) {\r
- bench = 0;\r
- bench_fps_s = bench_fps;\r
- bf[bfp++ & 3] = bench_fps;\r
- bench_fps = 0;\r
- }\r
- bench_fps += frames_shown;\r
- sprintf(fpsbuff, "%02i/%02i/%02i", frames_shown, bench_fps_s, (bf[0]+bf[1]+bf[2]+bf[3])>>2);\r
-#else\r
- if (currentConfig.EmuOpt & 2) {\r
- sprintf(fpsbuff, "%02i/%02i", frames_shown, frames_done);\r
- if (fpsbuff[5] == 0) { fpsbuff[5] = fpsbuff[6] = ' '; fpsbuff[7] = 0; }\r
- }\r
-#endif\r
- frames_shown = frames_done = 0;\r
- thissec = tval.tv_sec;\r
- }\r
-#ifdef PFRAMES\r
- sprintf(fpsbuff, "%i", Pico.m.frame_count);\r
-#endif\r
-\r
- if (pthissec != tval.tv_sec)\r
- {\r
- if (PsndOut == 0 && currentConfig.Frameskip >= 0) {\r
- pframes_done = pframes_shown = 0;\r
- } else {\r
- // it is quite common for this implementation to leave 1 fame unfinished\r
- // when second changes, but we don't want buffer to starve.\r
- if (PsndOut && pframes_done < target_fps && pframes_done > target_fps-5) {\r
- emu_update_input();\r
- SkipFrame(1); pframes_done++;\r
- }\r
-\r
- pframes_done -= target_fps; if (pframes_done < 0) pframes_done = 0;\r
- pframes_shown -= target_fps; if (pframes_shown < 0) pframes_shown = 0;\r
- if (pframes_shown > pframes_done) pframes_shown = pframes_done;\r
- }\r
- pthissec = tval.tv_sec;\r
- }\r