int main(int argc,char **argv) { #if defined(__GNUC__) && defined(__WIN32__) //HACK: workaround for precompiled SDL libraries that block output to console FILE * ctt = fopen("CON", "w" ); freopen( "CON", "w", stdout ); freopen( "CON", "w", stderr ); #endif // init basic flags before parsing args uzebox.sdl_flags = SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC; if(argc == 1) { showHelp(argv[0]); return 1; } int opt; char* heximage = NULL; while((opt = getopt_long(argc, argv,shortopts,longopts,NULL)) != -1) { switch(opt) { default: /* fallthrough */ case 'h': showHelp(argv[0]); return 1; case 'n': uzebox.enableSound = false; break; case 'f': uzebox.fullscreen = true; break; case 'w': uzebox.sdl_flags = (uzebox.sdl_flags & ~(SDL_RENDERER_ACCELERATED | SDL_RENDERER_PRESENTVSYNC)) | SDL_RENDERER_SOFTWARE; break; case 'v': uzebox.sdl_flags &= ~SDL_RENDERER_PRESENTVSYNC; break; case 'm': uzebox.pad_mode = avr8::SNES_MOUSE; break; case '2': uzebox.pad_mode = avr8::SNES_PAD2; break; #ifndef __EMSCRIPTEN__ case 'r': uzebox.recordMovie=true; break; #endif // __EMSCRIPTEN__ case 's': uzebox.SDpath = optarg; break; case 'e': uzebox.eepromFile=optarg; break; case 'b': uzebox.pc = 0x7800;//0xF000; //set start for boot image break; case 'c': uzebox.captureMode=CAPTURE_WRITE; break; case 'l': uzebox.captureMode=CAPTURE_READ; break; case 'z': uzebox.hsyncHelp=true; break; #ifndef NOGDB case 'd': uzebox.enableGdb = true; break; case 't': long port = strtol(optarg,NULL,10); if ((port == LONG_MAX) || (port == LONG_MIN) || (port < 0) || port > 65535) uzebox.gdbPort = 0; else uzebox.gdbPort = port; break; #endif // NOGDB } } // get leftovers for (int i = optind; i < argc; ++i) { if(heximage){ printerr("Error: HEX file already specified (too many arguments?).\n\n"); showHelp(argv[0]); return 1; } else{ heximage = argv[i]; } } #ifndef NOGDB if (uzebox.gdbPort == 0) { printerr("Error: invalid port address.\n\n"); showHelp(argv[0]); return 1; } #endif // NOGDB // start EEPROM emulation if appropriate if(uzebox.eepromFile){ uzebox.LoadEEPROMFile(uzebox.eepromFile); } // attempt to load the hex image if(!heximage){ printerr("Error: No HEX program or boot file specified.\n\n"); showHelp(argv[0]); return 1; } // write hex image if(heximage){ unsigned char* buffer = (unsigned char*)(uzebox.progmem); if(ends_with(heximage,"uze", 3)){ if(isUzeromFile(heximage)){ printf("-- Loading UzeROM Image --\n"); if(!loadUzeImage(heximage,&uzeRomHeader,buffer)){ printerr("Error: cannot load UzeRom file '%s'.\n\n",heximage); showHelp(argv[0]); return 1; } // enable mouse support if required if(uzeRomHeader.mouse){ uzebox.pad_mode = avr8::SNES_MOUSE; printf("Mouse support enabled\n"); } }else{ printerr("Error: Cannot load UZE ROM file '%s'. Bad format header?\n\n",heximage); showHelp(argv[0]); return 1; } }else{ printf("Loading Hex Image...\n"); if(!loadHex(heximage,buffer)){ printerr("Error: cannot load HEX image '%s'.\n\n",heximage); showHelp(argv[0]); return 1; } } uzebox.decodeFlash(); //get rom name without extension char *pfile = heximage + strlen(heximage); for (;; pfile--) { if ((*pfile == '\\') || (*pfile == '/') || pfile==heximage) { if(pfile!=heximage)pfile++; //skip the slash character for(int i=0;i<256;i++){ if(*pfile=='.') break; uzebox.romName[i]=*pfile; pfile++; } break; } } //build the capture file name int len=strlen(uzebox.romName); char capfname[len+5]; strcpy(capfname,uzebox.romName); capfname[len+0]='.'; capfname[len+1]='c'; capfname[len+2]='a'; capfname[len+3]='p'; capfname[len+4]=0; /* char capfname[256]; char *pfile = heximage + strlen(heximage); for (;; pfile--) { if ((*pfile == '\\') || (*pfile == '/') || pfile==heximage) { if(pfile!=heximage)pfile++; //skip the slash character for(int i=0;i<256;i++){ if(*pfile=='.'){ capfname[i+0]='.'; capfname[i+1]='c'; capfname[i+2]='a'; capfname[i+3]='p'; capfname[i+4]=0; break; } capfname[i]=*pfile; pfile++; } break; } } */ if(uzebox.captureMode==CAPTURE_READ) { uzebox.captureFile=fopen(capfname,"rb"); if(uzebox.captureFile==0){ uzebox.captureMode=CAPTURE_NONE; printerr("Warning: Cannot open capture file %s. Capture replay ignored.\n\n",capfname); }else{ fseek(uzebox.captureFile, 0L, SEEK_END); long fz = ftell(uzebox.captureFile); rewind(uzebox.captureFile); uzebox.captureData=new u8[fz]; uzebox.captureSize=fz; uzebox.capturePtr=0; fread(uzebox.captureData,1,fz,uzebox.captureFile); fclose(uzebox.captureFile); uzebox.captureFile = 0; } } else if(uzebox.captureMode==CAPTURE_WRITE) { uzebox.captureFile=fopen(capfname,"wb"); if(uzebox.captureFile==0){ uzebox.captureMode=CAPTURE_NONE; printerr("Error: Cannot open capture file %s.\n\n",capfname); return 1; } } //if user did not specify a path for the sd card, use the rom's path if(uzebox.SDpath == NULL){ //extract path char *pfile; pfile = heximage + strlen(heximage); for (;; pfile--) { if ((*pfile == '\\') || (*pfile == '/')) { *pfile=0; pfile = heximage; break; } if (pfile == heximage) { pfile[0] = '.'; pfile[1] = '/'; pfile[2] = 0; break; } } uzebox.SDpath=pfile; printf("\nUsing HEX path for SD emulation: %s\n",pfile); } } if (uzebox.SDpath != NULL) { if (!uzebox.init_sd()) { printerr("Error: cannot load directory for SD emulation '%s'.\n\n", uzebox.SDpath); showHelp(argv[0]); return 1; } } sprintf(uzebox.caption,"Uzebox Emulator " VERSION " (ESC=quit, F1=help)"); // init the GUI if (!uzebox.init_gui()){ printerr("Error: Failed to init GUI.\n\n"); showHelp(argv[0]); return 1; } #ifndef NOGDB if (uzebox.enableGdb == true) { #if defined(USE_GDBSERVER_DEBUG) uzebox.gdb = new GdbServer(&uzebox, uzebox.gdbPort, true, true); #else uzebox.gdb = new GdbServer(&uzebox, uzebox.gdbPort, false, true); #endif } else uzebox.state = CPU_RUNNING; #endif // NOGDB uzebox.randomSeed=time(NULL); srand(uzebox.randomSeed); //used for the watchdog timer entropy const int cycles=100000000; int left, now; #ifdef __EMSCRIPTEN__ emscripten_set_main_loop(one_iter, 60, 1); emscripten_set_main_loop_timing(EM_TIMING_RAF, 1); #else // __EMSCRIPTEN__ while (true) { if (uzebox.fullscreen){ puts(uzebox.caption); }else{ if (uzebox.window) SDL_SetWindowTitle(uzebox.window,uzebox.caption); } left = cycles; now = SDL_GetTicks(); while (left > 0) left -= uzebox.exec(); now = SDL_GetTicks() - now; sprintf(uzebox.caption,"Uzebox Emulator " VERSION " (ESC=quit, F1=help) %02d.%03d Mhz",cycles/now/1000,(cycles/now)%1000); } #endif // __EMSCRIPTEN__ return 0; }
int main(int argc,char **argv) { avr8 uzebox; bool disasmOnly = true; #if defined(__GNUC__) && defined(__WIN32__) //HACK: workaround for precompiled SDL libraries that block output to console freopen( "CONOUT$", "wt", stdout ); freopen( "CONOUT$", "wt", stderr ); #endif // init basic flags before parsing args uzebox.sdl_flags = SDL_DOUBLEBUF | SDL_SWSURFACE; if(argc == 1) { showHelp(argv[0]); return 1; } int opt; char* heximage = NULL; // char* eepromFile = NULL; int bootsize = 0; while((opt = getopt_long(argc, argv,shortopts,longopts,NULL)) != -1) { switch(opt) { default: /* fallthrough */ case 'h': showHelp(argv[0]); return 1; #if defined(DISASM) case 'k': uzebox.breakpoint = (u16) strtoul(optarg,NULL,16); break; #endif case 'n': uzebox.enableSound = false; break; case 'f': uzebox.fullscreen = true; break; case 'w': uzebox.sdl_flags = (uzebox.sdl_flags & ~SDL_SWSURFACE) | SDL_HWSURFACE; break; case 'x': uzebox.sdl_flags &= ~SDL_DOUBLEBUF; break; case 'i': uzebox.interlaced = true; break; case 'm': uzebox.pad_mode = avr8::SNES_MOUSE; break; case '2': uzebox.pad_mode = avr8::SNES_PAD2; break; case 'r': //TODO: implement MBR emulation option break; case 's': uzebox.SDpath = optarg; break; case 'e': //eepromFile = optarg; uzebox.eepromFile=optarg; break; case 'b': uzebox.pc = 0x7800;//0xF000; //set start for boot image break; case 'd': uzebox.enableGdb = true; break; case 't': long port = strtol(optarg,NULL,10); if ((port == LONG_MAX) || (port == LONG_MIN) || (port < 0) || port > 65535) uzebox.gdbPort = 0; else uzebox.gdbPort = port; break; } } // get leftovers for (int i = optind; i < argc; ++i) { if(heximage){ printerr("Error: HEX file already specified (too many arguments?).\n\n",heximage); showHelp(argv[0]); return 1; } else{ heximage = argv[i]; } } if (uzebox.gdbPort == 0) { printerr("Error: invalid port address.\n\n",uzebox.gdbPort); showHelp(argv[0]); return 1; } // start EEPROM emulation if appropriate if(uzebox.eepromFile){ uzebox.LoadEEPROMFile(uzebox.eepromFile); } // attempt to load the hex image if(!heximage){ printerr("Error: No HEX program or boot file specified.\n\n"); showHelp(argv[0]); return 1; } // write hex image if(heximage){ unsigned char* buffer = (unsigned char*)(uzebox.progmem); strlwr(heximage); if(ends_with(heximage,"uze", 3)){ if(isUzeromFile(heximage)){ printf("-- Loading UzeROM Image --\n"); if(!loadUzeImage(heximage,&uzeRomHeader,buffer)){ printerr("Error: cannot load UzeRom file '%s'.\n\n",heximage); showHelp(argv[0]); return 1; } // enable mouse support if required if(uzeRomHeader.mouse){ uzebox.pad_mode = avr8::SNES_MOUSE; printf("Mouse support enabled\n"); } }else{ printerr("Error: Cannot load UZE ROM file '%s'. Bad format header?\n\n",heximage); showHelp(argv[0]); return 1; } }else{ printf("Loading Hex Image...\n"); if(!loadHex(heximage,buffer)){ printerr("Error: cannot load HEX image '%s'.\n\n",heximage); showHelp(argv[0]); return 1; } } //if user did not specify a path for the sd card, use the rom's path if(uzebox.SDpath == NULL){ //extract path char *pfile; pfile = heximage + strlen(heximage); for (; pfile > heximage; pfile--) { if ((*pfile == '\\') || (*pfile == '/')) { *pfile=0; pfile = heximage; break; } } uzebox.SDpath=pfile; printf("\nUsing HEX path for SD emulation: %s\n",pfile); } } if (uzebox.SDpath != NULL) { if (!uzebox.init_sd()) { printerr("Error: cannot load directory for SD emulation '%s'.\n\n", uzebox.SDpath); showHelp(argv[0]); return 1; } } // init the GUI if (!uzebox.init_gui()){ printerr("Error: Failed to init GUI.\n\n"); showHelp(argv[0]); return 1; } if (uzebox.enableGdb == true) { #if defined(USE_GDBSERVER_DEBUG) uzebox.gdb = new GdbServer(&uzebox, uzebox.gdbPort, true, true); #else uzebox.gdb = new GdbServer(&uzebox, uzebox.gdbPort, false, true); #endif } else uzebox.state = CPU_RUNNING; const int cycles=100000000; int left, now; char caption[128]; while (true) { left = cycles; now = SDL_GetTicks(); while (left > 0) left -= uzebox.exec(); now = SDL_GetTicks() - now; sprintf(caption,"Uzebox Emulator " VERSION " (ESC=quit, F1=help) %02d.%03d Mhz",cycles/now/1000,(cycles/now)%1000); if (uzebox.fullscreen){ puts(caption); }else{ SDL_WM_SetCaption(caption, NULL); } } return 0; }