#include #include #include #include #ifdef M_CORE_GBA #include #endif #ifdef M_CORE_GB #include #endif #include #include #include #include struct msCoreController * msCoreControllerLoadGame (const unsigned char *rom, size_t rom_len, const unsigned char *state, size_t state_len, struct msClientConnectionData *const data) { struct VFile* file_rom = VFileMemChunk (NULL, rom_len); struct VFile* file_state = VFileMemChunk (NULL, state_len); file_rom->seek (file_rom, 0, SEEK_SET); file_state->seek (file_state, 0, SEEK_SET); file_rom->write (file_rom, rom, rom_len); file_state->write (file_state, state, state_len); struct mCore *core = mCoreFindVF (file_rom); struct msCoreController *controller = NULL; if (!core) { ms_last_error = "This rom does not appear to be a GBA or GB/C one"; file_rom->close(file_rom); file_state->close(file_rom); goto loadGameReturn; } core->init(core); unsigned int width; unsigned int height; mCoreInitConfig(core, NULL); mCoreConfigSetIntValue(&core->config, "logLevel", mLOG_FATAL); core->desiredVideoDimensions(core, &width, &height); color_t *outputBuffer = malloc((sizeof *outputBuffer) * width * height); printf("controller->outputBuffer width: %u\n", width); core->setVideoBuffer(core, outputBuffer, width); core->loadROM (core, file_rom); mCoreLoadStateNamed (core, file_state, SAVESTATE_SAVEDATA & SAVESTATE_RTC); controller = msCoreControllerNew (core, data); controller->outputBuffer = outputBuffer; controller->stride = width; loadGameReturn: return controller; } void msCoreControllerSetFrameCallback(struct msCoreController *const self, void(*callback)(struct mCoreThread *)) { self->threadContext.frameCallback = callback; } void msCoreControllerSetStartCallback(struct msCoreController *const self, void(*callback)(struct mCoreThread *)) { self->threadContext.startCallback = callback; } void msCoreControllerThreadStart (struct msCoreController *const core_controller) { struct mCoreThread *thread = &core_controller->threadContext; mCoreThreadStart(thread); } void msCoreControllerDestroy(struct msCoreController **controller_ptr) { if (controller_ptr && *controller_ptr) { struct msCoreController *controller = *controller_ptr; if (mCoreThreadHasStarted(&controller->threadContext) && !mCoreThreadHasExited(&controller->threadContext)) { mCoreThreadEnd(&controller->threadContext); } if (controller->threadContext.core) { struct mCore *core = controller->threadContext.core; core->deinit(core); } free(controller->outputBuffer); free(controller); *controller_ptr = NULL; } } struct msCoreController * msCoreControllerNew (struct mCore *core, struct msClientConnectionData *const data) { struct msCoreController *controller = malloc (sizeof *controller); controller->multiplayer = NULL; controller->threadContext.core = core; controller->threadContext.userData = data; return controller; }