mirror of
https://github.com/UberGames/ioef.git
synced 2025-01-31 04:50:37 +00:00
Allow VM_Restart to load unpure qagame.qvm so that local server won't crash after map_restart if server operator has qagame.qvm residing outside pak file (#5196)
Thanks to "rg3" for providing a shell account
This commit is contained in:
parent
d176ebe84a
commit
7eba074ce4
4 changed files with 27 additions and 21 deletions
|
@ -1081,7 +1081,7 @@ Returns filesize and an open FILE pointer.
|
||||||
*/
|
*/
|
||||||
extern qboolean com_fullyInitialized;
|
extern qboolean com_fullyInitialized;
|
||||||
|
|
||||||
long FS_FOpenFileReadDir(const char *filename, searchpath_t *search, fileHandle_t *file, qboolean uniqueFILE)
|
long FS_FOpenFileReadDir(const char *filename, searchpath_t *search, fileHandle_t *file, qboolean uniqueFILE, qboolean unpure)
|
||||||
{
|
{
|
||||||
long hash;
|
long hash;
|
||||||
pack_t *pak;
|
pack_t *pak;
|
||||||
|
@ -1190,7 +1190,7 @@ long FS_FOpenFileReadDir(const char *filename, searchpath_t *search, fileHandle_
|
||||||
if(search->pack->hashTable[hash])
|
if(search->pack->hashTable[hash])
|
||||||
{
|
{
|
||||||
// disregard if it doesn't match one of the allowed pure pak files
|
// disregard if it doesn't match one of the allowed pure pak files
|
||||||
if(!FS_PakIsPure(search->pack))
|
if(!unpure && !FS_PakIsPure(search->pack))
|
||||||
{
|
{
|
||||||
*file = 0;
|
*file = 0;
|
||||||
return -1;
|
return -1;
|
||||||
|
@ -1281,7 +1281,7 @@ long FS_FOpenFileReadDir(const char *filename, searchpath_t *search, fileHandle_
|
||||||
// this test can make the search fail although the file is in the directory
|
// this test can make the search fail although the file is in the directory
|
||||||
// I had the problem on https://zerowing.idsoftware.com/bugzilla/show_bug.cgi?id=8
|
// I had the problem on https://zerowing.idsoftware.com/bugzilla/show_bug.cgi?id=8
|
||||||
// turned out I used FS_FileExists instead
|
// turned out I used FS_FileExists instead
|
||||||
if(fs_numServerPaks)
|
if(!unpure && fs_numServerPaks)
|
||||||
{
|
{
|
||||||
if(!FS_IsExt(filename, ".cfg", len) && // for config files
|
if(!FS_IsExt(filename, ".cfg", len) && // for config files
|
||||||
!FS_IsExt(filename, ".menu", len) && // menu files
|
!FS_IsExt(filename, ".menu", len) && // menu files
|
||||||
|
@ -1341,7 +1341,7 @@ long FS_FOpenFileRead(const char *filename, fileHandle_t *file, qboolean uniqueF
|
||||||
|
|
||||||
for(search = fs_searchpaths; search; search = search->next)
|
for(search = fs_searchpaths; search; search = search->next)
|
||||||
{
|
{
|
||||||
len = FS_FOpenFileReadDir(filename, search, file, uniqueFILE);
|
len = FS_FOpenFileReadDir(filename, search, file, uniqueFILE, qfalse);
|
||||||
|
|
||||||
if(file == NULL)
|
if(file == NULL)
|
||||||
{
|
{
|
||||||
|
@ -1425,7 +1425,7 @@ vmInterpret_t FS_FindVM(void **startSearch, char *found, int foundlen, const cha
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(FS_FOpenFileReadDir(qvmName, search, NULL, qfalse) > 0)
|
if(FS_FOpenFileReadDir(qvmName, search, NULL, qfalse, qfalse) > 0)
|
||||||
{
|
{
|
||||||
*startSearch = search;
|
*startSearch = search;
|
||||||
return VMI_COMPILED;
|
return VMI_COMPILED;
|
||||||
|
@ -1447,7 +1447,7 @@ vmInterpret_t FS_FindVM(void **startSearch, char *found, int foundlen, const cha
|
||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
if(FS_FOpenFileReadDir(qvmName, search, NULL, qfalse) > 0)
|
if(FS_FOpenFileReadDir(qvmName, search, NULL, qfalse, qfalse) > 0)
|
||||||
{
|
{
|
||||||
*startSearch = search;
|
*startSearch = search;
|
||||||
|
|
||||||
|
@ -1752,7 +1752,7 @@ a null buffer will just return the file length without loading
|
||||||
If searchPath is non-NULL search only in that specific search path
|
If searchPath is non-NULL search only in that specific search path
|
||||||
============
|
============
|
||||||
*/
|
*/
|
||||||
long FS_ReadFileDir(const char *qpath, void *searchPath, void **buffer)
|
long FS_ReadFileDir(const char *qpath, void *searchPath, qboolean unpure, void **buffer)
|
||||||
{
|
{
|
||||||
fileHandle_t h;
|
fileHandle_t h;
|
||||||
searchpath_t *search;
|
searchpath_t *search;
|
||||||
|
@ -1825,7 +1825,7 @@ long FS_ReadFileDir(const char *qpath, void *searchPath, void **buffer)
|
||||||
else
|
else
|
||||||
{
|
{
|
||||||
// look for it in a specific search path only
|
// look for it in a specific search path only
|
||||||
len = FS_FOpenFileReadDir(qpath, search, &h, qfalse);
|
len = FS_FOpenFileReadDir(qpath, search, &h, qfalse, unpure);
|
||||||
}
|
}
|
||||||
|
|
||||||
if ( h == 0 ) {
|
if ( h == 0 ) {
|
||||||
|
@ -1884,7 +1884,7 @@ a null buffer will just return the file length without loading
|
||||||
*/
|
*/
|
||||||
long FS_ReadFile(const char *qpath, void **buffer)
|
long FS_ReadFile(const char *qpath, void **buffer)
|
||||||
{
|
{
|
||||||
return FS_ReadFileDir(qpath, NULL, buffer);
|
return FS_ReadFileDir(qpath, NULL, qfalse, buffer);
|
||||||
}
|
}
|
||||||
|
|
||||||
/*
|
/*
|
||||||
|
@ -2751,7 +2751,7 @@ qboolean FS_Which(const char *filename, void *searchPath)
|
||||||
{
|
{
|
||||||
searchpath_t *search = searchPath;
|
searchpath_t *search = searchPath;
|
||||||
|
|
||||||
if(FS_FOpenFileReadDir(filename, search, NULL, qfalse) > 0)
|
if(FS_FOpenFileReadDir(filename, search, NULL, qfalse, qfalse) > 0)
|
||||||
{
|
{
|
||||||
if(search->pack)
|
if(search->pack)
|
||||||
{
|
{
|
||||||
|
|
|
@ -363,7 +363,7 @@ void VM_Free( vm_t *vm );
|
||||||
void VM_Clear(void);
|
void VM_Clear(void);
|
||||||
void VM_Forced_Unload_Start(void);
|
void VM_Forced_Unload_Start(void);
|
||||||
void VM_Forced_Unload_Done(void);
|
void VM_Forced_Unload_Done(void);
|
||||||
vm_t *VM_Restart( vm_t *vm );
|
vm_t *VM_Restart(vm_t *vm, qboolean unpure);
|
||||||
|
|
||||||
intptr_t QDECL VM_Call( vm_t *vm, int callNum, ... );
|
intptr_t QDECL VM_Call( vm_t *vm, int callNum, ... );
|
||||||
|
|
||||||
|
@ -663,7 +663,7 @@ int FS_Read( void *buffer, int len, fileHandle_t f );
|
||||||
void FS_FCloseFile( fileHandle_t f );
|
void FS_FCloseFile( fileHandle_t f );
|
||||||
// note: you can't just fclose from another DLL, due to MS libc issues
|
// note: you can't just fclose from another DLL, due to MS libc issues
|
||||||
|
|
||||||
long FS_ReadFileDir(const char *qpath, void *searchPath, void **buffer);
|
long FS_ReadFileDir(const char *qpath, void *searchPath, qboolean unpure, void **buffer);
|
||||||
long FS_ReadFile(const char *qpath, void **buffer);
|
long FS_ReadFile(const char *qpath, void **buffer);
|
||||||
// returns the length of the file
|
// returns the length of the file
|
||||||
// a null buffer will just return the file length without loading
|
// a null buffer will just return the file length without loading
|
||||||
|
|
|
@ -363,7 +363,8 @@ VM_LoadQVM
|
||||||
Load a .qvm file
|
Load a .qvm file
|
||||||
=================
|
=================
|
||||||
*/
|
*/
|
||||||
vmHeader_t *VM_LoadQVM( vm_t *vm, qboolean alloc ) {
|
vmHeader_t *VM_LoadQVM( vm_t *vm, qboolean alloc, qboolean unpure)
|
||||||
|
{
|
||||||
int dataLength;
|
int dataLength;
|
||||||
int i;
|
int i;
|
||||||
char filename[MAX_QPATH];
|
char filename[MAX_QPATH];
|
||||||
|
@ -376,7 +377,7 @@ vmHeader_t *VM_LoadQVM( vm_t *vm, qboolean alloc ) {
|
||||||
Com_sprintf( filename, sizeof(filename), "vm/%s.qvm", vm->name );
|
Com_sprintf( filename, sizeof(filename), "vm/%s.qvm", vm->name );
|
||||||
Com_Printf( "Loading vm file %s...\n", filename );
|
Com_Printf( "Loading vm file %s...\n", filename );
|
||||||
|
|
||||||
FS_ReadFileDir(filename, vm->searchPath, &header.v);
|
FS_ReadFileDir(filename, vm->searchPath, unpure, &header.v);
|
||||||
|
|
||||||
if ( !header.h ) {
|
if ( !header.h ) {
|
||||||
Com_Printf( "Failed.\n" );
|
Com_Printf( "Failed.\n" );
|
||||||
|
@ -522,9 +523,13 @@ VM_Restart
|
||||||
|
|
||||||
Reload the data, but leave everything else in place
|
Reload the data, but leave everything else in place
|
||||||
This allows a server to do a map_restart without changing memory allocation
|
This allows a server to do a map_restart without changing memory allocation
|
||||||
|
|
||||||
|
We need to make sure that servers can access unpure QVMs (not contained in any pak)
|
||||||
|
even if the client is pure, so take "unpure" as argument.
|
||||||
=================
|
=================
|
||||||
*/
|
*/
|
||||||
vm_t *VM_Restart( vm_t *vm ) {
|
vm_t *VM_Restart(vm_t *vm, qboolean unpure)
|
||||||
|
{
|
||||||
vmHeader_t *header;
|
vmHeader_t *header;
|
||||||
|
|
||||||
// DLL's can't be restarted in place
|
// DLL's can't be restarted in place
|
||||||
|
@ -542,15 +547,16 @@ vm_t *VM_Restart( vm_t *vm ) {
|
||||||
}
|
}
|
||||||
|
|
||||||
// load the image
|
// load the image
|
||||||
Com_Printf( "VM_Restart()\n" );
|
Com_Printf("VM_Restart()\n");
|
||||||
|
|
||||||
if( !( header = VM_LoadQVM( vm, qfalse ) ) ) {
|
if(!(header = VM_LoadQVM(vm, qfalse, unpure)))
|
||||||
Com_Error( ERR_DROP, "VM_Restart failed" );
|
{
|
||||||
|
Com_Error(ERR_DROP, "VM_Restart failed");
|
||||||
return NULL;
|
return NULL;
|
||||||
}
|
}
|
||||||
|
|
||||||
// free the original file
|
// free the original file
|
||||||
FS_FreeFile( header );
|
FS_FreeFile(header);
|
||||||
|
|
||||||
return vm;
|
return vm;
|
||||||
}
|
}
|
||||||
|
@ -621,7 +627,7 @@ vm_t *VM_Create( const char *module, intptr_t (*systemCalls)(intptr_t *),
|
||||||
else if(retval == VMI_COMPILED)
|
else if(retval == VMI_COMPILED)
|
||||||
{
|
{
|
||||||
vm->searchPath = startSearch;
|
vm->searchPath = startSearch;
|
||||||
if((header = VM_LoadQVM(vm, qtrue)))
|
if((header = VM_LoadQVM(vm, qtrue, qfalse)))
|
||||||
break;
|
break;
|
||||||
|
|
||||||
// VM_Free overwrites the name on failed load
|
// VM_Free overwrites the name on failed load
|
||||||
|
|
|
@ -901,7 +901,7 @@ void SV_RestartGameProgs( void ) {
|
||||||
VM_Call( gvm, GAME_SHUTDOWN, qtrue );
|
VM_Call( gvm, GAME_SHUTDOWN, qtrue );
|
||||||
|
|
||||||
// do a restart instead of a free
|
// do a restart instead of a free
|
||||||
gvm = VM_Restart( gvm );
|
gvm = VM_Restart(gvm, qtrue);
|
||||||
if ( !gvm ) {
|
if ( !gvm ) {
|
||||||
Com_Error( ERR_FATAL, "VM_Restart on game failed" );
|
Com_Error( ERR_FATAL, "VM_Restart on game failed" );
|
||||||
}
|
}
|
||||||
|
|
Loading…
Reference in a new issue