live cart reloading fixes #374
This commit is contained in:
		@@ -618,12 +618,13 @@ static s32 saveProject(Console* console, void* buffer)
 | 
				
			|||||||
	return strlen(stream);
 | 
						return strlen(stream);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void loadTextSection(const char* project, const char* tag, void* dst, s32 size)
 | 
					static bool loadTextSection(const char* project, const char* tag, void* dst, s32 size)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	char tagbuf[64];
 | 
						char tagbuf[64];
 | 
				
			||||||
	sprintf(tagbuf, "-- <%s>\n", tag);
 | 
						sprintf(tagbuf, "-- <%s>\n", tag);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	const char* start = SDL_strstr(project, tagbuf);
 | 
						const char* start = SDL_strstr(project, tagbuf);
 | 
				
			||||||
 | 
						bool done = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if(start)
 | 
						if(start)
 | 
				
			||||||
	{
 | 
						{
 | 
				
			||||||
@@ -635,17 +636,23 @@ static void loadTextSection(const char* project, const char* tag, void* dst, s32
 | 
				
			|||||||
			const char* end = SDL_strstr(start, tagbuf);
 | 
								const char* end = SDL_strstr(start, tagbuf);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
			if(end > start)
 | 
								if(end > start)
 | 
				
			||||||
 | 
								{
 | 
				
			||||||
				SDL_memcpy(dst, start, SDL_min(size, end - start));
 | 
									SDL_memcpy(dst, start, SDL_min(size, end - start));
 | 
				
			||||||
 | 
									done = true;
 | 
				
			||||||
			}
 | 
								}
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return done;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void loadBinarySection(const char* project, const char* tag, s32 count, void* dst, s32 size, bool flip)
 | 
					static bool loadBinarySection(const char* project, const char* tag, s32 count, void* dst, s32 size, bool flip)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	char tagbuf[64];
 | 
						char tagbuf[64];
 | 
				
			||||||
	sprintf(tagbuf, "-- <%s>\n", tag);
 | 
						sprintf(tagbuf, "-- <%s>\n", tag);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	const char* start = SDL_strstr(project, tagbuf);
 | 
						const char* start = SDL_strstr(project, tagbuf);
 | 
				
			||||||
 | 
						bool done = false;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	if(start)
 | 
						if(start)
 | 
				
			||||||
	{
 | 
						{
 | 
				
			||||||
@@ -680,8 +687,12 @@ static void loadBinarySection(const char* project, const char* tag, s32 count, v
 | 
				
			|||||||
				ptr += sizeof("-- 999:") - 1;
 | 
									ptr += sizeof("-- 999:") - 1;
 | 
				
			||||||
				str2buf(ptr, end - ptr, (u8*)dst, flip);
 | 
									str2buf(ptr, end - ptr, (u8*)dst, flip);
 | 
				
			||||||
			}
 | 
								}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
								done = true;
 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return done;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static bool loadProject(Console* console, const char* data, s32 size, tic_cartridge* dst)
 | 
					static bool loadProject(Console* console, const char* data, s32 size, tic_cartridge* dst)
 | 
				
			||||||
@@ -710,21 +721,22 @@ static bool loadProject(Console* console, const char* data, s32 size, tic_cartri
 | 
				
			|||||||
			SDL_memset(cart, 0, sizeof(tic_cartridge));
 | 
								SDL_memset(cart, 0, sizeof(tic_cartridge));
 | 
				
			||||||
			SDL_memcpy(&cart->palette, &tic->config.palette.data, sizeof(tic_palette));
 | 
								SDL_memcpy(&cart->palette, &tic->config.palette.data, sizeof(tic_palette));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
			loadTextSection(project, "CODE", cart->code.data, sizeof(tic_code));
 | 
								if(loadTextSection(project, "CODE", cart->code.data, sizeof(tic_code)))
 | 
				
			||||||
 | 
									done = true;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
			for(s32 i = 0; i < COUNT_OF(BinarySections); i++)
 | 
								for(s32 i = 0; i < COUNT_OF(BinarySections); i++)
 | 
				
			||||||
			{
 | 
								{
 | 
				
			||||||
				const BinarySection* section = &BinarySections[i];
 | 
									const BinarySection* section = &BinarySections[i];
 | 
				
			||||||
				loadBinarySection(project, section->tag, section->count, (u8*)cart + section->offset, section->size, section->flip);
 | 
									if(loadBinarySection(project, section->tag, section->count, (u8*)cart + section->offset, section->size, section->flip))
 | 
				
			||||||
 | 
										done = true;
 | 
				
			||||||
			}
 | 
								}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
			loadBinarySection(project, "COVER", 1, &cart->cover, -1, true);
 | 
								if(loadBinarySection(project, "COVER", 1, &cart->cover, -1, true))
 | 
				
			||||||
 | 
									done = true;
 | 
				
			||||||
			
 | 
								
 | 
				
			||||||
			SDL_memcpy(dst, cart, sizeof(tic_cartridge));
 | 
								SDL_memcpy(dst, cart, sizeof(tic_cartridge));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
			SDL_free(cart);
 | 
								SDL_free(cart);
 | 
				
			||||||
 | 
					 | 
				
			||||||
			done = true;
 | 
					 | 
				
			||||||
		}
 | 
							}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
		SDL_free(project);
 | 
							SDL_free(project);
 | 
				
			||||||
@@ -744,11 +756,22 @@ static void updateProject(Console* console)
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
		if(data)
 | 
							if(data)
 | 
				
			||||||
		{
 | 
							{
 | 
				
			||||||
			loadProject(console, data, size, &tic->cart);
 | 
								tic_cartridge* cart = SDL_malloc(sizeof(tic_cartridge));
 | 
				
			||||||
			SDL_free(data);
 | 
					
 | 
				
			||||||
 | 
								if(cart)
 | 
				
			||||||
 | 
								{
 | 
				
			||||||
 | 
									if(loadProject(console, data, size, cart))
 | 
				
			||||||
 | 
									{
 | 
				
			||||||
 | 
										SDL_memcpy(&tic->cart, cart, sizeof(tic_cartridge));
 | 
				
			||||||
 | 
					
 | 
				
			||||||
					studioRomLoaded();
 | 
										studioRomLoaded();
 | 
				
			||||||
				}
 | 
									}
 | 
				
			||||||
 | 
									
 | 
				
			||||||
 | 
									SDL_free(cart);
 | 
				
			||||||
 | 
								}
 | 
				
			||||||
 | 
								SDL_free(data);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
							}		
 | 
				
			||||||
	}
 | 
						}
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										12
									
								
								src/fs.c
									
									
									
									
									
								
							
							
						
						
									
										12
									
								
								src/fs.c
									
									
									
									
									
								
							@@ -618,6 +618,18 @@ bool fsExistsFile(FileSystem* fs, const char* name)
 | 
				
			|||||||
	return fsExists(getFilePath(fs, name));
 | 
						return fsExists(getFilePath(fs, name));
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					u64 fsMDate(FileSystem* fs, const char* name)
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						struct tic_stat_struct s;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						if(tic_stat(UTF8ToString(getFilePath(fs, name)), &s) == 0 && S_ISREG(s.st_mode))
 | 
				
			||||||
 | 
						{
 | 
				
			||||||
 | 
							return s.st_mtime;
 | 
				
			||||||
 | 
						}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						return 0;
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool fsSaveFile(FileSystem* fs, const char* name, const void* data, size_t size, bool overwrite)
 | 
					bool fsSaveFile(FileSystem* fs, const char* name, const void* data, size_t size, bool overwrite)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	if(!overwrite)
 | 
						if(!overwrite)
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										1
									
								
								src/fs.h
									
									
									
									
									
								
							
							
						
						
									
										1
									
								
								src/fs.h
									
									
									
									
									
								
							@@ -60,6 +60,7 @@ void* fsLoadFile(FileSystem* fs, const char* name, s32* size);
 | 
				
			|||||||
void* fsLoadRootFile(FileSystem* fs, const char* name, s32* size);
 | 
					void* fsLoadRootFile(FileSystem* fs, const char* name, s32* size);
 | 
				
			||||||
void fsMakeDir(FileSystem* fs, const char* name);
 | 
					void fsMakeDir(FileSystem* fs, const char* name);
 | 
				
			||||||
bool fsExistsFile(FileSystem* fs, const char* name);
 | 
					bool fsExistsFile(FileSystem* fs, const char* name);
 | 
				
			||||||
 | 
					u64 fsMDate(FileSystem* fs, const char* name);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
const char* fsBasename(const char *path);
 | 
					const char* fsBasename(const char *path);
 | 
				
			||||||
const char* fsFilename(const char *path);
 | 
					const char* fsFilename(const char *path);
 | 
				
			||||||
 
 | 
				
			|||||||
							
								
								
									
										37
									
								
								src/studio.c
									
									
									
									
									
								
							
							
						
						
									
										37
									
								
								src/studio.c
									
									
									
									
									
								
							@@ -78,7 +78,11 @@ static struct
 | 
				
			|||||||
	tic80_local* tic80local;
 | 
						tic80_local* tic80local;
 | 
				
			||||||
	tic_mem* tic;
 | 
						tic_mem* tic;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						struct
 | 
				
			||||||
 | 
						{
 | 
				
			||||||
		CartHash hash;
 | 
							CartHash hash;
 | 
				
			||||||
 | 
							u64 mdate;
 | 
				
			||||||
 | 
						}cart;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	SDL_Window* window;
 | 
						SDL_Window* window;
 | 
				
			||||||
	SDL_Renderer* renderer;
 | 
						SDL_Renderer* renderer;
 | 
				
			||||||
@@ -199,6 +203,11 @@ static struct
 | 
				
			|||||||
	.texture = NULL,
 | 
						.texture = NULL,
 | 
				
			||||||
	.audioDevice = 0,
 | 
						.audioDevice = 0,
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
						.cart = 
 | 
				
			||||||
 | 
						{
 | 
				
			||||||
 | 
							.mdate = 0,
 | 
				
			||||||
 | 
						},
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	.joysticks = {NULL, NULL, NULL, NULL},
 | 
						.joysticks = {NULL, NULL, NULL, NULL},
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	.mode = TIC_START_MODE,
 | 
						.mode = TIC_START_MODE,
 | 
				
			||||||
@@ -919,7 +928,12 @@ static void initModules()
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
static void updateHash()
 | 
					static void updateHash()
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	md5(&studio.tic->cart, sizeof(tic_cartridge), studio.hash.data);
 | 
						md5(&studio.tic->cart, sizeof(tic_cartridge), studio.cart.hash.data);
 | 
				
			||||||
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					static void updateMDate()
 | 
				
			||||||
 | 
					{
 | 
				
			||||||
 | 
						studio.cart.mdate = fsMDate(studio.console.fs, studio.console.romName);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void updateTitle()
 | 
					static void updateTitle()
 | 
				
			||||||
@@ -936,6 +950,7 @@ void studioRomSaved()
 | 
				
			|||||||
{
 | 
					{
 | 
				
			||||||
	updateTitle();
 | 
						updateTitle();
 | 
				
			||||||
	updateHash();
 | 
						updateHash();
 | 
				
			||||||
 | 
						updateMDate();
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
void studioRomLoaded()
 | 
					void studioRomLoaded()
 | 
				
			||||||
@@ -944,6 +959,7 @@ void studioRomLoaded()
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
	updateTitle();
 | 
						updateTitle();
 | 
				
			||||||
	updateHash();
 | 
						updateHash();
 | 
				
			||||||
 | 
						updateMDate();
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
bool studioCartChanged()
 | 
					bool studioCartChanged()
 | 
				
			||||||
@@ -951,7 +967,7 @@ bool studioCartChanged()
 | 
				
			|||||||
	CartHash hash;
 | 
						CartHash hash;
 | 
				
			||||||
	md5(&studio.tic->cart, sizeof(tic_cartridge), hash.data);
 | 
						md5(&studio.tic->cart, sizeof(tic_cartridge), hash.data);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
	return memcmp(hash.data, studio.hash.data, sizeof(CartHash)) != 0;
 | 
						return memcmp(hash.data, studio.cart.hash.data, sizeof(CartHash)) != 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void updateGamepadParts();
 | 
					static void updateGamepadParts();
 | 
				
			||||||
@@ -1682,12 +1698,16 @@ static void processMouseInput()
 | 
				
			|||||||
	studio.tic->ram.vram.input.gamepad.pressed = studio.mouse.state->down ? 1 : 0;
 | 
						studio.tic->ram.vram.input.gamepad.pressed = studio.mouse.state->down ? 1 : 0;
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#if defined(TIC80_PRO)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
static void reloadConfirm(bool yes, void* data)
 | 
					static void reloadConfirm(bool yes, void* data)
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	if(yes)
 | 
						if(yes)
 | 
				
			||||||
		studio.console.updateProject(&studio.console);
 | 
							studio.console.updateProject(&studio.console);
 | 
				
			||||||
}
 | 
					}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
					#endif
 | 
				
			||||||
 | 
					
 | 
				
			||||||
SDL_Event* pollEvent()
 | 
					SDL_Event* pollEvent()
 | 
				
			||||||
{
 | 
					{
 | 
				
			||||||
	static SDL_Event event;
 | 
						static SDL_Event event;
 | 
				
			||||||
@@ -1733,6 +1753,12 @@ SDL_Event* pollEvent()
 | 
				
			|||||||
#if defined(TIC80_PRO)
 | 
					#if defined(TIC80_PRO)
 | 
				
			||||||
 | 
					
 | 
				
			||||||
				if(studio.mode != TIC_START_MODE)
 | 
									if(studio.mode != TIC_START_MODE)
 | 
				
			||||||
 | 
									{
 | 
				
			||||||
 | 
										Console* console = &studio.console;
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
										u64 mdate = fsMDate(console->fs, console->romName);
 | 
				
			||||||
 | 
					
 | 
				
			||||||
 | 
										if(mdate > studio.cart.mdate)
 | 
				
			||||||
					{
 | 
										{
 | 
				
			||||||
						if(studioCartChanged())
 | 
											if(studioCartChanged())
 | 
				
			||||||
						{
 | 
											{
 | 
				
			||||||
@@ -1747,13 +1773,14 @@ SDL_Event* pollEvent()
 | 
				
			|||||||
 | 
					
 | 
				
			||||||
							showDialog(Rows, COUNT_OF(Rows), reloadConfirm, NULL);
 | 
												showDialog(Rows, COUNT_OF(Rows), reloadConfirm, NULL);
 | 
				
			||||||
						}
 | 
											}
 | 
				
			||||||
					else studio.console.updateProject(&studio.console);					
 | 
											else console->updateProject(console);						
 | 
				
			||||||
 | 
										}
 | 
				
			||||||
				}
 | 
									}
 | 
				
			||||||
 | 
					
 | 
				
			||||||
#endif
 | 
					#endif
 | 
				
			||||||
				{
 | 
									{
 | 
				
			||||||
					studio.console.codeLiveReload.reload(&studio.console,studio.code.data);
 | 
										studio.console.codeLiveReload.reload(&studio.console, studio.code.data);
 | 
				
			||||||
					if(studio.code.update)
 | 
										if(studio.console.codeLiveReload.active && studio.code.update)
 | 
				
			||||||
						studio.code.update(&studio.code);
 | 
											studio.code.update(&studio.code);
 | 
				
			||||||
				}
 | 
									}
 | 
				
			||||||
				break;
 | 
									break;
 | 
				
			||||||
 
 | 
				
			|||||||
		Reference in New Issue
	
	Block a user