qboolean __cdecl Com_LoadDvarsFromBuffer(const char **inputbuf, unsigned int length, const char *data_p, const char *filename) { const char *cvar_name; int i, count; char buf[16384]; const char* line; Com_Memset(buf, 0, sizeof(buf)); for(i = 0; i < length; i++) { Cvar_Reset(inputbuf[i]); } Com_BeginParseSession(filename); count = 0; while ( (cvar_name = Com_Parse(&data_p)) && cvar_name[0]) { for(i = 0; i < length; i++) { if(!Q_stricmp(cvar_name, inputbuf[i])) break; } if(i == length) { if(com_developer && com_developer->integer) { Com_PrintWarning("WARNING: unknown cvar '%s' in file '%s'\n", cvar_name, filename); } Com_SkipRestOfLine(&data_p); }else{ line = Com_ParseOnLine(&data_p); if(com_developer && com_developer->integer) { Cvar_Set(inputbuf[i], line); }else{ if((!Q_strncmp(inputbuf[i],"bg_shock_viewKickPeriod", 23) || !Q_strncmp(inputbuf[i],"bg_shock_viewKickFadeTime", 25)) && (line[0] == '0' && line[1] == '\0')) { /* Quite this spam */ }else{ Cvar_Set(inputbuf[i], line); } } if ( !buf[i] ) { buf[i] = 1; ++count; } } } Com_EndParseSession(); if ( length == count ) { /* No Errors */ return 1; } Com_PrintError("ERROR: the following cvars were not specified in file '%s'\n", filename); for(i = 0; i < length; i++) { while ( buf[i] && i < length ) { ++i; } if(i < length) Com_PrintError(" %s\n", inputbuf[i]); } return 0; }
/* ============ GetWavinfo ============ */ wavinfo_t GetWavinfo(char *name, byte *wav, int wavlength) { wavinfo_t info; int i; int format; int samples; memset(&info, 0, sizeof(info)); if (!wav) { return info; } iff_data = wav; iff_end = wav + wavlength; // find "RIFF" chunk FindChunk("RIFF"); if (!(data_p && !Q_strncmp(data_p+8, "WAVE", 4))) { Con_Printf("Missing RIFF/WAVE chunks\n"); return info; } // get "fmt " chunk iff_data = data_p + 12; // DumpChunks (); FindChunk("fmt "); if (!data_p) { Con_Printf("Missing fmt chunk\n"); return info; } data_p += 8; format = GetLittleShort(); if (format != 1) { Con_Printf("Microsoft PCM format only\n"); return info; } info.channels = GetLittleShort(); info.rate = GetLittleLong(); data_p += 4+2; info.width = GetLittleShort() / 8; // get cue chunk FindChunk("cue "); if (data_p) { data_p += 32; info.loopstart = GetLittleLong(); // Con_Printf("loopstart=%d\n", sfx->loopstart); // if the next chunk is a LIST chunk, look for a cue length marker FindNextChunk("LIST"); if (data_p) { if (!strncmp(data_p + 28, "mark", 4)) { // this is not a proper parse, but it works with cooledit... data_p += 24; i = GetLittleLong(); // samples in loop info.samples = info.loopstart + i; // Con_Printf("looped length: %i\n", i); } } } else { info.loopstart = -1; } // find data chunk FindChunk("data"); if (!data_p) { Con_Printf("Missing data chunk\n"); return info; } data_p += 4; samples = GetLittleLong() / info.width; if (info.samples) { if (samples < info.samples) { Sys_Error("Sound %s has a bad loop length", name); } } else { info.samples = samples; } info.dataofs = data_p - wav; return info; }
/* ================= Mod_LoadFaces ================= */ void Mod_LoadFaces (lump_t *l) { dface_t *in; msurface_t *out; int i, count, surfnum; int planenum, side; in = (void *)(mod_base + l->fileofs); if (l->filelen % sizeof(*in)) Sys_Error ("MOD_LoadBmodel: funny lump size in %s",loadmodel->name); count = l->filelen / sizeof(*in); out = Hunk_AllocName ( count*sizeof(*out), loadname); loadmodel->surfaces = out; loadmodel->numsurfaces = count; for ( surfnum=0 ; surfnum<count ; surfnum++, in++, out++) { out->firstedge = LittleLong(in->firstedge); out->numedges = LittleShort(in->numedges); out->flags = 0; planenum = LittleShort(in->planenum); side = LittleShort(in->side); if (side) out->flags |= SURF_PLANEBACK; out->plane = loadmodel->planes + planenum; out->texinfo = loadmodel->texinfo + LittleShort (in->texinfo); CalcSurfaceExtents (out); // lighting info for (i=0 ; i<MAXLIGHTMAPS ; i++) out->styles[i] = in->styles[i]; i = LittleLong(in->lightofs); if (i == -1) out->samples = NULL; else out->samples = loadmodel->lightdata + i; // set the drawing flags flag if (!Q_strncmp(out->texinfo->texture->name,"sky",3)) // sky { out->flags |= (SURF_DRAWSKY | SURF_DRAWTILED); continue; } if (!Q_strncmp(out->texinfo->texture->name,"*",1)) // turbulent { out->flags |= (SURF_DRAWTURB | SURF_DRAWTILED); for (i=0 ; i<2 ; i++) { out->extents[i] = 16384; out->texturemins[i] = -8192; } continue; } } }
/* =================== G_SpawnGEntityFromSpawnVars Spawn an entity and fill in all of the level fields from level.spawnVars[], then call the class specfic spawn function =================== */ void G_SpawnGEntityFromSpawnVars( qboolean inSubBSP ) { int i; gentity_t *ent; char *s, *value, *gametypeName; static char *gametypeNames[] = {"ffa", "holocron", "jedimaster", "duel", "powerduel", "single", "team", "siege", "ctf", "cty"}; // get the next free entity ent = G_Spawn(); for ( i = 0 ; i < level.numSpawnVars ; i++ ) { G_ParseField( level.spawnVars[i][0], level.spawnVars[i][1], ent ); } // check for "notsingle" flag if ( g_gametype.integer == GT_SINGLE_PLAYER ) { G_SpawnInt( "notsingle", "0", &i ); if ( i ) { ADJUST_AREAPORTAL(); G_FreeEntity( ent ); return; } } // check for "notteam" flag (GT_FFA, GT_DUEL, GT_SINGLE_PLAYER) if ( g_gametype.integer >= GT_TEAM ) { G_SpawnInt( "notteam", "0", &i ); if ( i ) { ADJUST_AREAPORTAL(); G_FreeEntity( ent ); return; } } else { G_SpawnInt( "notfree", "0", &i ); if ( i ) { ADJUST_AREAPORTAL(); G_FreeEntity( ent ); return; } } if( G_SpawnString( "gametype", NULL, &value ) ) { if( g_gametype.integer >= GT_FFA && g_gametype.integer < GT_MAX_GAME_TYPE ) { gametypeName = gametypeNames[g_gametype.integer]; s = strstr( value, gametypeName ); if( !s ) { ADJUST_AREAPORTAL(); G_FreeEntity( ent ); return; } } } // move editor origin to pos VectorCopy( ent->s.origin, ent->s.pos.trBase ); VectorCopy( ent->s.origin, ent->r.currentOrigin ); // if we didn't get a classname, don't bother spawning anything if ( !G_CallSpawn( ent ) ) { G_FreeEntity( ent ); } //Tag on the ICARUS scripting information only to valid recipients if ( trap_ICARUS_ValidEnt( ent ) ) { trap_ICARUS_InitEnt( ent ); if ( ent->classname && ent->classname[0] ) { if ( Q_strncmp( "NPC_", ent->classname, 4 ) != 0 ) {//Not an NPC_spawner (rww - probably don't even care for MP, but whatever) G_ActivateBehavior( ent, BSET_SPAWN ); } } } }
/* <40e38> ../engine/info.c:72 */ void Info_RemoveKey(char *s, const char *key) { char pkey[MAX_KV_LEN]; char value[MAX_KV_LEN]; char *start; char *c; int cmpsize; int nCount; if (Q_strstr(key, "\\")) { Con_Printf("Can't use a key with a \\\n"); return; } cmpsize = Q_strlen(key); if (cmpsize > MAX_KV_LEN - 1) cmpsize = MAX_KV_LEN - 1; while (*s) { start = s; if (*s == '\\') { s++; // skip the slash } // Copy a key nCount = 0; c = pkey; while (*s != '\\') { if (!*s) { break; // key should end with a \, not a NULL, but allow to remove it } if (nCount >= MAX_KV_LEN) { s++; continue; // skip oversized key chars till the slash or EOL } *c++ = *s++; nCount++; } *c = 0; if (*s) s++; // skip the slash // Copy a value nCount = 0; c = value; while (*s != '\\') { if (!*s) { break; // allow value to be ended with NULL } if (nCount >= MAX_KV_LEN) { s++; continue; // skip oversized value chars till the slash or EOL } *c++ = *s++; nCount++; } *c = 0; // Compare keys if (!Q_strncmp(key, pkey, cmpsize)) { strcpy_safe(start, s); // remove this part s = start; // continue searching } } }
/* ================= Q_strcmp ================= */ int Q_strcmp (const char *string1, const char *string2){ return Q_strncmp(string1, string2, 99999); }
void Svcmd_BanUser_f( void ) { char str[MAX_TOKEN_CHARS]; char userInfo[MAX_TOKEN_CHARS]; idFilter_t id; int playerNum; char *ip; if ( trap_Argc() < 2 ) { G_Printf("Usage: banUser <client ID> <reason for banning>\n"); return; } trap_Argv( 1, str, sizeof( str ) ); playerNum = atoi(str); if ( playerNum > MAX_CLIENTS || playerNum < 0 || !g_entities[playerNum].client ) { G_Printf("Error: Player ID wasn't valid.\n"); return; } trap_GetUserinfo( playerNum, userInfo, sizeof( userInfo ) ); if ( !userInfo[0] ) return; //get unique Ban ID id.playerID = atoul( Info_ValueForKey( userInfo, "sv_securityCode" ) ); //Get player name and clean it of color tags Q_strncpyz( id.playerName, Q_CleanStr(Info_ValueForKey( userInfo, "name" )), sizeof( id.playerName ) ); //get ban reason trap_Argv( 2, id.banReason, sizeof( id.banReason ) ); if ( !id.banReason[0] ) Q_strncpyz( id.banReason, "No reason given.", sizeof( id.banReason ) ); AddID( &id ); ip = g_entities[playerNum].client->pers.ip; UpdateIDBans(); //Scooter's filter list if( Q_stricmp( ip, "localhost" ) //localhost && Q_strncmp( ip, "10.", 3 ) //class A && Q_strncmp( ip, "172.16.", 7 ) //class B && Q_strncmp( ip, "192.168.", 8 ) //class C && Q_strncmp( ip, "127.", 4 ) //loopback && Q_strncmp( ip, "169.254.", 8 ) //link-local ) { AddIP( ip ); G_Printf( "User: %s ( %i - %s ) ^7was successfully banned.\n", Info_ValueForKey( userInfo, "name" ), playerNum, ip ); } trap_DropClient( playerNum, "Banned from the server" ); G_Printf( "User: %s ( %i ) ^7was successfully banned.\n", id.playerName, playerNum ); }
/** * @brief SDL_main * @param[in] argc * @param[in] argv * @return */ int main(int argc, char **argv) { char commandLine[MAX_STRING_CHARS] = { 0 }; Sys_PlatformInit(); // Set the initial time base Sys_Milliseconds(); #ifdef __APPLE__ // This is passed if we are launched by double-clicking if (argc >= 2 && Q_strncmp(argv[1], "-psn", 4) == 0) { argc = 1; } #endif Sys_ParseArgs(argc, argv); #if defined(__APPLE__) && !defined(DEDICATED) // argv[0] would be /Users/seth/etlegacy/etl.app/Contents/MacOS // But on OS X we want to pretend the binary path is the .app's parent // So that way the base folder is right next to the .app allowing { char parentdir[1024]; CFURLRef url = CFBundleCopyBundleURL(CFBundleGetMainBundle()); if (!url) { Sys_Dialog(DT_ERROR, "A CFURL for the app bundle could not be found.", "Can't set Sys_SetBinaryPath"); Sys_Exit(EXIT_FAILURE); } CFURLRef url2 = CFURLCreateCopyDeletingLastPathComponent(0, url); if (!url2 || !CFURLGetFileSystemRepresentation(url2, 1, (UInt8 *)parentdir, 1024)) { Sys_Dialog(DT_ERROR, "CFURLGetFileSystemRepresentation returned an error when finding the app bundle's parent directory.", "Can't set Sys_SetBinaryPath"); Sys_Exit(EXIT_FAILURE); } Sys_SetBinaryPath(parentdir); CFRelease(url); CFRelease(url2); } #else Sys_SetBinaryPath(Sys_Dirname(argv[0])); #endif Sys_SetDefaultInstallPath(DEFAULT_BASEDIR); // Sys_BinaryPath() by default // Concatenate the command line for passing to Com_Init Sys_BuildCommandLine(argc, argv, commandLine, sizeof(commandLine)); Com_Init(commandLine); NET_Init(); Sys_SetUpConsoleAndSignals(); #ifdef _WIN32 #ifndef DEDICATED if (com_viewlog->integer) { Sys_ShowConsoleWindow(1, qfalse); } #endif Sys_Splash(qfalse); { char cwd[MAX_OSPATH]; _getcwd(cwd, sizeof(cwd)); Com_Printf("Working directory: %s\n", cwd); } // hide the early console since we've reached the point where we // have a working graphics subsystems #ifndef LEGACY_DEBUG if (!com_dedicated->integer && !com_viewlog->integer) { Sys_ShowConsoleWindow(0, qfalse); } #endif #endif Sys_GameLoop(); return EXIT_SUCCESS; }
/* ================= main ================= */ int main( int argc, char **argv ) { int i; char commandLine[ MAX_STRING_CHARS ] = { 0 }; #ifndef DEDICATED // SDL version check // Compile time # if !SDL_VERSION_ATLEAST(MINSDL_MAJOR,MINSDL_MINOR,MINSDL_PATCH) # error A more recent version of SDL is required # endif // Run time SDL_version ver; SDL_GetVersion( &ver ); #define MINSDL_VERSION \ XSTRING(MINSDL_MAJOR) "." \ XSTRING(MINSDL_MINOR) "." \ XSTRING(MINSDL_PATCH) if( SDL_VERSIONNUM( ver.major, ver.minor, ver.patch ) < SDL_VERSIONNUM( MINSDL_MAJOR, MINSDL_MINOR, MINSDL_PATCH ) ) { Sys_Dialog( DT_ERROR, va( "SDL version " MINSDL_VERSION " or greater is required, " "but only version %d.%d.%d was found. You may be able to obtain a more recent copy " "from http://www.libsdl.org/.", ver.major, ver.minor, ver.patch ), "SDL Library Too Old" ); Sys_Exit( 1 ); } SDL_EventState( SDL_DROPFILE, SDL_ENABLE ); #endif Sys_PlatformInit( ); // Set the initial time base Sys_Milliseconds( ); #ifdef __APPLE__ // This is passed if we are launched by double-clicking if ( argc >= 2 && Q_strncmp ( argv[1], "-psn", 4 ) == 0 ) argc = 1; #endif Sys_ParseArgs( argc, argv ); Sys_SetBinaryPath( Sys_Dirname( argv[ 0 ] ) ); Sys_SetDefaultInstallPath( DEFAULT_BASEDIR ); // Concatenate the command line for passing to Com_Init for( i = 1; i < argc; i++ ) { const qboolean containsSpaces = strchr(argv[i], ' ') != NULL; if (containsSpaces) Q_strcat( commandLine, sizeof( commandLine ), "\"" ); Q_strcat( commandLine, sizeof( commandLine ), argv[ i ] ); if (containsSpaces) Q_strcat( commandLine, sizeof( commandLine ), "\"" ); Q_strcat( commandLine, sizeof( commandLine ), " " ); } Com_Init( commandLine ); NET_Init( ); CON_Init( ); signal( SIGILL, Sys_SigHandler ); signal( SIGFPE, Sys_SigHandler ); signal( SIGSEGV, Sys_SigHandler ); signal( SIGTERM, Sys_SigHandler ); signal( SIGINT, Sys_SigHandler ); #if !defined DEDICATED && !defined MACOS_X && !defined WIN32 // HACK: Before SDL 2.0.4, Linux (X11) did not set numlock or capslock state // so I made the engine always assumed num lock was on. // NOTE: The SDL mod state on X11 is not set at this point even when it's fixed // and will be corrected regardless of what is done here, // but limit to SDL 2.0.3 and earlier so that the message isn't shown. if( SDL_VERSIONNUM( ver.major, ver.minor, ver.patch ) < SDL_VERSIONNUM( 2, 0, 4 ) ) { if ( !( SDL_GetModState() & KMOD_NUM ) ) { Com_Printf("INFO: Forcing NUMLOCK modifier state to enabled (actual state unknown)!\n"); SDL_SetModState( SDL_GetModState() | KMOD_NUM ); } } #endif while( 1 ) { IN_Frame( ); Com_Frame( ); } return 0; }
//============================================================================ // // Parameter: - // Returns: - // Changes Globals: - //============================================================================ int PS_ReadPunctuation(script_t *script, token_t *token) { int len; const char *p; punctuation_t *punc; #ifdef PUNCTABLE for (punc = script->punctuationtable[(unsigned int)*script->script_p]; punc; punc = punc->next) { #else int i; for (i = 0; script->punctuations[i].p; i++) { punc = &script->punctuations[i]; #endif //PUNCTABLE p = punc->p; len = strlen(p); //if the script contains at least as much characters as the punctuation if (script->script_p + len <= script->end_p) { //if the script contains the punctuation if (!Q_strncmp(script->script_p, p, len)) { strncpy(token->string, p, MAX_TOKEN); script->script_p += len; token->type = TT_PUNCTUATION; //sub type is the number of the punctuation token->subtype = punc->n; return 1; } //end if } //end if } //end for return 0; } //end of the function PS_ReadPunctuation //============================================================================ // // Parameter: - // Returns: - // Changes Globals: - //============================================================================ int PS_ReadPrimitive(script_t *script, token_t *token) { int len; len = 0; while(*script->script_p > ' ' && *script->script_p != ';') { if (len >= MAX_TOKEN - 1) { ScriptError(script, "primitive token longer than MAX_TOKEN = %d", MAX_TOKEN); return 0; } //end if token->string[len++] = *script->script_p++; } //end while token->string[len] = 0; //copy the token into the script structure Com_Memcpy(&script->token, token, sizeof(token_t)); //primitive reading successfull return 1; } //end of the function PS_ReadPrimitive
int HTTPServer_ReadMessage(netadr_t* from, msg_t* msg, ftRequest_t* request) { char stringlinebuf[MAX_STRING_CHARS]; byte* newbuf; char* line; int newsize, i; qboolean gotheader; if (request->recvmsg.maxsize - request->recvmsg.cursize < msg->cursize) { if(request->finallen != -1) { newsize = request->finallen; }else { newsize = 2 * request->recvmsg.maxsize + msg->cursize; } newbuf = Z_Malloc(newsize); if(newbuf == NULL) { return -1; } Com_Memcpy(newbuf, request->recvmsg.data, request->recvmsg.cursize); Z_Free(request->recvmsg.data); request->recvmsg.data = newbuf; request->recvmsg.maxsize = newsize; } Com_Memcpy(&request->recvmsg.data[request->recvmsg.cursize], msg->data, msg->cursize); request->recvmsg.cursize += msg->cursize; /* Is header complete ? */ if(request->finallen == -1) { gotheader = qfalse; /* 1st check if the header is complete */ while ((line = MSG_ReadStringLine(&request->recvmsg, stringlinebuf, sizeof(stringlinebuf))) && line[0] != '\0' ) { if(line[0] == '\r') { gotheader = qtrue; break; } } if(gotheader == qfalse) { return 0; } MSG_BeginReading(&request->recvmsg); line = MSG_ReadStringLine(&request->recvmsg, stringlinebuf, sizeof(stringlinebuf)); if (!Q_strncmp(line, "HEAD", 4)) { request->mode = HTTP_HEAD; line += 5; }else if (!Q_strncmp(line, "POST", 4)) { request->mode = HTTP_POST; line += 5; }else if (!Q_strncmp(line, "GET", 3)) { request->mode = HTTP_GET; line += 4; }else { Com_DPrintf("Invalid HTTP method from %s\n", NET_AdrToString(from)); return -1; } i = 0; while (*line != ' ' && *line != '\r' && *line) { request->url[i] = *line; i++; line++; } if(*line == ' ') { line++; } if(Q_stricmpn(line,"HTTP/1.",7) || isInteger(line + 7, 2) == qfalse || isInteger(line + 9, 4) == qfalse) { Com_PrintError("HTTP_ReceiveData: Packet is corrupt!\nDebug: %s\n", line); return -1; } request->version = atoi(line + 7); if (request->version != 0 && request->version != 1) { Com_PrintError("HTTP_ReceiveData: Packet has unknown HTTP version 1.%d !\n", request->version); return -1; } request->contentLength = 0; while ((line = MSG_ReadStringLine(&request->recvmsg, stringlinebuf, sizeof(stringlinebuf))) && line[0] != '\0' && line[0] != '\r') { if(!Q_stricmpn("Content-Length:", line, 15)) { if(isInteger(line + 15, 0) == qfalse) { Com_PrintError("Sec_GetHTTPPacket: Packet is corrupt!\nDebug: %s\n", line); return -1; } request->contentLength = atoi(line + 15); if(request->contentLength < 0) { request->contentLength = 0; return -1; } } else if(!Q_stricmpn("Content-Type:", line, 13)) { if(line[13] == ' ') { Q_strncpyz(request->contentType, &line[14], sizeof(request->contentType)); }else{ Q_strncpyz(request->contentType, &line[13], sizeof(request->contentType)); } } else if(!Q_stricmpn("Cookie:", line, 7)) { if(line[7] == ' ') { Q_strncpyz(request->cookie, &line[8], sizeof(request->cookie)); }else{ Q_strncpyz(request->cookie, &line[7], sizeof(request->cookie)); } } } if(line[0] == '\0') return -1; request->headerLength = request->recvmsg.readcount; request->finallen = request->contentLength + request->headerLength; if(request->finallen > 1024*1024*640) { request->finallen = request->headerLength; } } if(request->recvmsg.maxsize == request->finallen) request->transferactive = qtrue; if (request->recvmsg.cursize < request->finallen) { /* Still needing bytes... */ return 0; } // Com_Printf("^6HTTP-Message is complete!\n"); // Com_Printf("^6Received: Version: HTTP/1.%d Method: %d Content-Length: %d URL: %s\n", request->version, request->mode, request->contentLength, request->url); return 1; }
qboolean Delta_ParseField( char **delta_script, const delta_field_t *pInfo, delta_t *pField, qboolean bPost ) { string token; delta_field_t *pFieldInfo; char *oldpos; *delta_script = COM_ParseFile( *delta_script, token ); if( Q_strcmp( token, "(" )) { MsgDev( D_ERROR, "Delta_ParseField: expected '(', found '%s' instead\n", token ); return false; } // read the variable name if(( *delta_script = COM_ParseFile( *delta_script, token )) == NULL ) { MsgDev( D_ERROR, "Delta_ParseField: missing field name\n" ); return false; } pFieldInfo = Delta_FindFieldInfo( pInfo, token ); if( !pFieldInfo ) { MsgDev( D_ERROR, "Delta_ParseField: unable to find field %s\n", token ); return false; } *delta_script = COM_ParseFile( *delta_script, token ); if( Q_strcmp( token, "," )) { MsgDev( D_ERROR, "Delta_ParseField: expected ',', found '%s' instead\n", token ); return false; } // copy base info to new field pField->name = pFieldInfo->name; pField->offset = pFieldInfo->offset; pField->size = pFieldInfo->size; pField->flags = 0; // read delta-flags while(( *delta_script = COM_ParseFile( *delta_script, token )) != NULL ) { if( !Q_strcmp( token, "," )) break; // end of flags argument if( !Q_strcmp( token, "|" )) continue; if( !Q_strcmp( token, "DT_BYTE" )) pField->flags |= DT_BYTE; else if( !Q_strcmp( token, "DT_SHORT" )) pField->flags |= DT_SHORT; else if( !Q_strcmp( token, "DT_FLOAT" )) pField->flags |= DT_FLOAT; else if( !Q_strcmp( token, "DT_INTEGER" )) pField->flags |= DT_INTEGER; else if( !Q_strcmp( token, "DT_ANGLE" )) pField->flags |= DT_ANGLE; else if( !Q_strncmp( token, "DT_TIMEWINDOW", 13 )) pField->flags |= DT_TIMEWINDOW; else if( !Q_strcmp( token, "DT_STRING" )) pField->flags |= DT_STRING; else if( !Q_strcmp( token, "DT_SIGNED" )) pField->flags |= DT_SIGNED; } if( Q_strcmp( token, "," )) { MsgDev( D_ERROR, "Delta_ParseField: expected ',', found '%s' instead\n", token ); return false; } // read delta-bits if(( *delta_script = COM_ParseFile( *delta_script, token )) == NULL ) { MsgDev( D_ERROR, "Delta_ReadField: %s field bits argument is missing\n", pField->name ); return false; } pField->bits = Q_atoi( token ); *delta_script = COM_ParseFile( *delta_script, token ); if( Q_strcmp( token, "," )) { MsgDev( D_ERROR, "Delta_ReadField: expected ',', found '%s' instead\n", token ); return false; } // read delta-multiplier if(( *delta_script = COM_ParseFile( *delta_script, token )) == NULL ) { MsgDev( D_ERROR, "Delta_ReadField: %s missing 'multiplier' argument\n", pField->name ); return false; } pField->multiplier = Q_atof( token ); if( bPost ) { *delta_script = COM_ParseFile( *delta_script, token ); if( Q_strcmp( token, "," )) { MsgDev( D_ERROR, "Delta_ReadField: expected ',', found '%s' instead\n", token ); return false; } // read delta-postmultiplier if(( *delta_script = COM_ParseFile( *delta_script, token )) == NULL ) { MsgDev( D_ERROR, "Delta_ReadField: %s missing 'post_multiply' argument\n", pField->name ); return false; } pField->post_multiplier = Q_atof( token ); } else { // to avoid division by zero pField->post_multiplier = 1.0f; } // closing brace... *delta_script = COM_ParseFile( *delta_script, token ); if( Q_strcmp( token, ")" )) { MsgDev( D_ERROR, "Delta_ParseField: expected ')', found '%s' instead\n", token ); return false; } // ... and trying to parse optional ',' post-symbol oldpos = *delta_script; *delta_script = COM_ParseFile( *delta_script, token ); if( token[0] != ',' ) *delta_script = oldpos; // not a ',' return true; }
//----------------------------------------------------------------------------- // Purpose: //----------------------------------------------------------------------------- void CPhysMagnet::Touch( CBaseEntity *pOther ) { // Ignore triggers if ( pOther->IsSolidFlagSet( FSOLID_NOT_SOLID ) ) return; m_bHasHitSomething = true; // Don't pickup if we're not active if ( !m_bActive ) return; // Hit our maximum? if ( m_iMaxObjectsAttached && m_iMaxObjectsAttached <= GetNumAttachedObjects() ) return; // Make sure it's made of metal trace_t tr = GetTouchTrace(); char cTexType = TEXTURETYPE_Find( &tr ); if ( cTexType != CHAR_TEX_METAL && cTexType != CHAR_TEX_COMPUTER ) { // See if the model is set to be metal if ( Q_strncmp( Studio_GetDefaultSurfaceProps( GetModelPtr() ), "metal", 5 ) ) return; } IPhysicsObject *pPhysics = pOther->VPhysicsGetObject(); if ( pPhysics && pOther->GetMoveType() == MOVETYPE_VPHYSICS && pPhysics->IsMoveable() ) { // Make sure we haven't already got this sucker on the magnet int iCount = m_MagnettedEntities.Count(); for ( int i = 0; i < iCount; i++ ) { if ( m_MagnettedEntities[i].hEntity == pOther ) return; } // We want to cast a long way to ensure our shadow shows up pOther->SetShadowCastDistance( 2048 ); // Create a constraint between the magnet and this sucker IPhysicsObject *pMagnetPhysObject = VPhysicsGetObject(); Assert( pMagnetPhysObject ); magnetted_objects_t newEntityOnMagnet; newEntityOnMagnet.hEntity = pOther; // Use the right constraint if ( HasSpawnFlags( SF_MAGNET_ALLOWROTATION ) ) { constraint_ballsocketparams_t ballsocket; ballsocket.Defaults(); ballsocket.constraint.Defaults(); ballsocket.constraint.forceLimit = lbs2kg(m_forceLimit); ballsocket.constraint.torqueLimit = lbs2kg(m_torqueLimit); pMagnetPhysObject->WorldToLocal( ballsocket.constraintPosition[0], tr.endpos ); pPhysics->WorldToLocal( ballsocket.constraintPosition[1], tr.endpos ); //newEntityOnMagnet.pConstraint = physenv->CreateBallsocketConstraint( pMagnetPhysObject, pPhysics, m_pConstraintGroup, ballsocket ); newEntityOnMagnet.pConstraint = physenv->CreateBallsocketConstraint( pMagnetPhysObject, pPhysics, NULL, ballsocket ); } else { constraint_fixedparams_t fixed; fixed.Defaults(); fixed.InitWithCurrentObjectState( pMagnetPhysObject, pPhysics ); fixed.constraint.Defaults(); fixed.constraint.forceLimit = lbs2kg(m_forceLimit); fixed.constraint.torqueLimit = lbs2kg(m_torqueLimit); // FIXME: Use the magnet's constraint group. //newEntityOnMagnet.pConstraint = physenv->CreateFixedConstraint( pMagnetPhysObject, pPhysics, m_pConstraintGroup, fixed ); newEntityOnMagnet.pConstraint = physenv->CreateFixedConstraint( pMagnetPhysObject, pPhysics, NULL, fixed ); } newEntityOnMagnet.pConstraint->SetGameData( (void *) this ); m_MagnettedEntities.AddToTail( newEntityOnMagnet ); m_flTotalMass += pPhysics->GetMass(); } DoMagnetSuck( pOther ); m_OnMagnetAttach.FireOutput( this, this ); }
void *Sys_LoadDll( const char *name, char *fqpath, int( **entryPoint ) ( int, ... ), int ( *systemcalls )( int, ... ) ) { void *libHandle; void ( *dllEntry )( int ( *syscallptr )( int, ... ) ); char fname[MAX_OSPATH]; char *pwdpath; char *homepath; char *basepath; char *gamedir; char *fn; const char* err = NULL; // bk001206 // rb0101023 - now const #if !defined( DEDICATED ) char *cvar_name = NULL; #endif *fqpath = 0 ; // added 2/15/02 by T.Ray // bk001206 - let's have some paranoia assert( name ); Q_strncpyz( fname, Sys_GetDLLName( name ), sizeof( fname ) ); // bk001129 - was RTLD_LAZY #define Q_RTLD RTLD_NOW pwdpath = Sys_Cwd(); homepath = Cvar_VariableString( "fs_homepath" ); basepath = Cvar_VariableString( "fs_basepath" ); gamedir = Cvar_VariableString( "fs_game" ); // this is relevant to client only // this code is in for full client hosting a game, but it's not affected by it #if !defined( DEDICATED ) // do a first scan to identify what we are going to dlopen // we need to pass this to FS_ExtractFromPakFile so that it checksums the right file // NOTE: if something fails (not found, or file operation failed), we will ERR_FATAL (in the checksum itself, we only ERR_DROP) #ifndef NDEBUG fn = FS_BuildOSPath( pwdpath, gamedir, fname ); if ( access( fn, R_OK ) == -1 ) { #endif fn = FS_BuildOSPath( homepath, gamedir, fname ); if ( access( fn, R_OK ) == 0 ) { // there is a .so in fs_homepath, but is it a valid one version-wise? // we use a persistent variable in config.cfg to make sure // this is set in FS_CL_ExtractFromPakFile when the file is extracted cvar_t *lastVersion; cvar_name = va( "cl_lastVersion%s", name ); lastVersion = Cvar_Get( cvar_name, "(uninitialized)", CVAR_ARCHIVE ); if ( Q_stricmp( Cvar_VariableString( "version" ), lastVersion->string ) ) { Com_DPrintf( "clearing non matching version of %s .so: %s\n", name, fn ); if ( remove( fn ) == -1 ) { Com_Error( ERR_FATAL, "failed to remove outdated '%s' file:\n\"%s\"\n", fn, strerror( errno ) ); } // we cancelled fs_homepath, go work on basepath now fn = FS_BuildOSPath( basepath, gamedir, fname ); if ( access( fn, R_OK ) == -1 ) { // we may be dealing with a media-only mod, check wether we can find 'reference' DLLs and copy them over if ( !CopyDLLForMod( &fn, gamedir, pwdpath, homepath, basepath, fname ) ) { Com_Error( ERR_FATAL, "Sys_LoadDll(%s) failed, no corresponding .so file found in fs_homepath or fs_basepath\n", name ); } } } // the .so in fs_homepath is valid version-wise .. FS_CL_ExtractFromPakFile will have to decide wether it's valid pk3-wise later } else { fn = FS_BuildOSPath( basepath, gamedir, fname ); if ( access( fn, R_OK ) == -1 ) { // we may be dealing with a media-only mod, check wether we can find 'reference' DLLs and copy them over if ( !CopyDLLForMod( &fn, gamedir, pwdpath, homepath, basepath, fname ) ) { Com_Error( ERR_FATAL, "Sys_LoadDll(%s) failed, no corresponding .so file found in fs_homepath or fs_basepath\n", name ); } } } #ifndef NDEBUG } #endif // NERVE - SMF - extract dlls from pak file for security // we have to handle the game dll a little differently // NOTE #2: we may have found a file in fs_basepath, and if the checksum is wrong, FS_Extract will write in fs_homepath // won't be a problem since we start a brand new scan next if ( cl_connectedToPureServer && Q_strncmp( name, "qagame", 6 ) ) { if ( !FS_CL_ExtractFromPakFile( fn, gamedir, fname, cvar_name ) ) { Com_Error( ERR_DROP, "Game code(%s) failed Pure Server check", fname ); } } #endif #ifndef NDEBUG // current directory // NOTE: only for debug build, see Sys_LoadDll discussion fn = FS_BuildOSPath( pwdpath, gamedir, fname ); Com_Printf( "Sys_LoadDll(%s)... ", fn ); libHandle = dlopen( fn, Q_RTLD ); if ( !libHandle ) { Com_Printf( "\nSys_LoadDll(%s) failed:\n\"%s\"\n", fn, dlerror() ); #endif // homepath fn = FS_BuildOSPath( homepath, gamedir, fname ); Com_Printf( "Sys_LoadDll(%s)... ", fn ); libHandle = dlopen( fn, Q_RTLD ); if ( !libHandle ) { Com_Printf( "\nSys_LoadDll(%s) failed:\n\"%s\"\n", fn, dlerror() ); // basepath fn = FS_BuildOSPath( basepath, gamedir, fname ); Com_Printf( "Sys_LoadDll(%s)... ", fn ); libHandle = dlopen( fn, Q_RTLD ); if ( !libHandle ) { // report any problem Com_Printf( "\nSys_LoadDll(%s) failed:\n\"%s\"\n", fn, dlerror() ); } else { Com_Printf( "ok\n" ); } // not found, bail if ( !libHandle ) { #ifndef NDEBUG // in debug abort on failure Com_Error( ERR_FATAL, "Sys_LoadDll(%s) failed dlopen() completely!\n", name ); #else Com_Printf( "Sys_LoadDll(%s) failed dlopen() completely!\n", name ); #endif return NULL; } } else { Com_Printf( "ok\n" ); } #ifndef NDEBUG } else { Com_Printf( "ok\n" ); } #endif Q_strncpyz( fqpath, fn, MAX_QPATH ) ; // added 2/15/02 by T.Ray dllEntry = dlsym( libHandle, "dllEntry" ); *entryPoint = dlsym( libHandle, "vmMain" ); if ( !*entryPoint || !dllEntry ) { err = dlerror(); #ifndef NDEBUG // in debug abort on failure Com_Error( ERR_FATAL, "Sys_LoadDll(%s) failed dlsym(vmMain):\n\"%s\" !\n", name, err ); #else Com_Printf( "Sys_LoadDll(%s) failed dlsym(vmMain):\n\"%s\" !\n", name, err ); #endif dlclose( libHandle ); err = dlerror(); if ( err != NULL ) { Com_Printf( "Sys_LoadDll(%s) failed dlcose:\n\"%s\"\n", name, err ); } return NULL; } Com_Printf( "Sys_LoadDll(%s) found **vmMain** at %p \n", name, *entryPoint ); dllEntry( systemcalls ); Com_Printf( "Sys_LoadDll(%s) succeeded!\n", name ); return libHandle; }
/* ================= SV_LoadGame_f ================= */ void SV_LoadGame_f(void) { char filename[MAX_QPATH], mapname[MAX_QPATH], savedir[MAX_QPATH]; byte *buffer; int size; char *cl_profileStr = Cvar_VariableString("cl_profile"); // dont allow command if another loadgame is pending if (Cvar_VariableIntegerValue("savegame_loading")) { return; } if (sv_reloading->integer) { // (SA) disabling // if(sv_reloading->integer && sv_reloading->integer != RELOAD_FAILED ) // game is in 'reload' mode, don't allow starting new maps yet. return; } Q_strncpyz(filename, Cmd_Argv(1), sizeof(filename)); if (!filename[0]) { Com_Printf("You must specify a savegame to load\n"); return; } if (com_gameInfo.usesProfiles && cl_profileStr[0]) { Com_sprintf(savedir, sizeof(savedir), "profiles/%s/save/", cl_profileStr); } else { Q_strncpyz(savedir, "save/", sizeof(savedir)); } /*if ( Q_strncmp( filename, "save/", 5 ) && Q_strncmp( filename, "save\\", 5 ) ) { Q_strncpyz( filename, va("save/%s", filename), sizeof( filename ) ); }*/ // go through a va to avoid vsnprintf call with same source and target Q_strncpyz(filename, va("%s%s", savedir, filename), sizeof(filename)); // enforce .sav extension if (!strstr(filename, ".") || Q_strncmp(strstr(filename, ".") + 1, "sav", 3)) { Q_strcat(filename, sizeof(filename), ".sav"); } // use '/' instead of '\\' for directories while (strstr(filename, "\\")) { *(char *)strstr(filename, "\\") = '/'; } size = FS_ReadFile(filename, NULL); if (size < 0) { Com_Printf("Can't find savegame %s\n", filename); return; } //buffer = Hunk_AllocateTempMemory(size); FS_ReadFile(filename, (void **)&buffer); // read the mapname, if it is the same as the current map, then do a fast load Com_sprintf(mapname, sizeof(mapname), (const char *)(buffer + sizeof(int))); if (com_sv_running->integer && (com_frameTime != sv.serverId)) { // check mapname if (!Q_stricmp(mapname, sv_mapname->string)) // same { if (Q_stricmp(filename, va("%scurrent.sav", savedir)) != 0) { // copy it to the current savegame file FS_WriteFile(va("%scurrent.sav", savedir), buffer, size); } Hunk_FreeTempMemory(buffer); Cvar_Set("savegame_loading", "2"); // 2 means it's a restart, so stop rendering until we are loaded // set the filename Cvar_Set("savegame_filename", filename); // quick-restart the server SV_MapRestart_f(); // savegame will be loaded after restart return; } } Hunk_FreeTempMemory(buffer); // otherwise, do a slow load if (Cvar_VariableIntegerValue("sv_cheats")) { Cbuf_ExecuteText(EXEC_APPEND, va("spdevmap %s", filename)); } else // no cheats { Cbuf_ExecuteText(EXEC_APPEND, va("spmap %s", filename)); } }
void Webadmin_BuildServerStatus(xml_t* xmlobj, qboolean showfullguid) { int i, numcl; client_t* cl; char strbuf[MAX_STRING_CHARS]; char colorbuf[2048]; mvabuf; char teamallies[32]; char teamaxis[32]; gclient_t *gclient; qboolean teambased = qfalse; qboolean ffabased = qfalse; numcl = 0; for (cl = svs.clients, gclient = level.clients, i = 0; i < sv_maxclients->integer; i++, cl++, gclient++) { if (cl->state < CS_CONNECTED) { continue; } if(gclient->sess.sessionTeam == TEAM_RED || gclient->sess.sessionTeam == TEAM_BLUE) { teambased = qtrue; break; } if(gclient->sess.sessionTeam == TEAM_FREE) { ffabased = qtrue; break; } } XO1("table","class","table table-striped table-bordered cod4xtable"); XA("<th>CID</th><th>Name</th><th>UID/GUID</th><th>Power</th><th>Score</th><th>Ping</th>"); if(teambased) { if(!Q_strncmp(g_TeamName_Axis->string,"MPUI_SPETSNAZ", 13)) Q_strncpyz(teamaxis, "Spetsnaz", sizeof(teamaxis)); else if(!Q_strncmp(g_TeamName_Axis->string,"MPUI_OPFOR", 10)) Q_strncpyz(teamaxis, "Opfor", sizeof(teamaxis)); else Q_strncpyz(teamaxis, g_TeamName_Axis->string, sizeof(teamaxis)); if(!Q_strncmp(g_TeamName_Allies->string,"MPUI_MARINES", 12)) Q_strncpyz(teamallies, "Marines", sizeof(teamallies)); else if(!Q_strncmp(g_TeamName_Allies->string,"MPUI_SAS", 8)) Q_strncpyz(teamallies, "S.A.S.", sizeof(teamallies)); else Q_strncpyz(teamallies, g_TeamName_Allies->string, sizeof(teamallies)); XO("tr"); XO1("td", "colspan", "6"); XA(teamaxis); XC; XC; for (cl = svs.clients, gclient = level.clients, i = 0; i < sv_maxclients->integer; i++, cl++, gclient++) { if (cl->state < CS_CONNECTED) { continue; } if(gclient->sess.sessionTeam != TEAM_RED) { continue; } ++numcl; XO("tr"); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", i);//CID XA(strbuf); XO("td");//Name XA(Webadmin_ConvertToHTMLColor(cl->name, colorbuf, sizeof(colorbuf))); XC; XO("td");//GUID if(cl->uid > 0) { XA(va("%d", cl->uid)); } else { if(showfullguid) XA(cl->pbguid); else XA(&cl->pbguid[24]); } XC; Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->power);//Ping XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", gclient->pers.scoreboard.score);//Score XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->ping);//Ping XA(strbuf); XC; } XO("tr"); XO1("td", "colspan", "6"); XA(teamallies); XC; XC; for (cl = svs.clients, gclient = level.clients, i = 0; i < sv_maxclients->integer; i++, cl++, gclient++) { if (cl->state < CS_CONNECTED) { continue; } if(gclient->sess.sessionTeam != TEAM_BLUE) { continue; } ++numcl; XO("tr"); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", i);//CID XA(strbuf); XO("td");//Name XA(Webadmin_ConvertToHTMLColor(cl->name, colorbuf, sizeof(colorbuf))); XC; XO("td");//GUID if(cl->uid > 0) { XA(va("%d", cl->uid)); } else { if(showfullguid) XA(cl->pbguid); else XA(&cl->pbguid[24]); } XC; Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->power);//Ping XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", gclient->pers.scoreboard.score);//Score XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->ping);//Ping XA(strbuf); XC; } } else if(ffabased) { XO("tr"); XO1("td", "colspan", "6"); XA("Players"); XC; XC; for (cl = svs.clients, gclient = level.clients, i = 0; i < sv_maxclients->integer; i++, cl++, gclient++) { if (cl->state < CS_CONNECTED) { continue; } if(gclient->sess.sessionTeam != TEAM_FREE) { continue; } ++numcl; XO("tr"); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", i);//CID XA(strbuf); XO("td");//Name XA(Webadmin_ConvertToHTMLColor(cl->name, colorbuf, sizeof(colorbuf))); XC; XO("td");//GUID if(cl->uid > 0) { XA(va("%d", cl->uid)); } else { if(showfullguid) XA(cl->pbguid); else XA(&cl->pbguid[24]); } XC; Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->power);//Ping XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", gclient->pers.scoreboard.score);//Score XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->ping);//Ping XA(strbuf); XC; } } XO("tr"); XO1("td", "colspan", "6"); XA("Spectators"); XC; XC; for (cl = svs.clients, gclient = level.clients, i = 0; i < sv_maxclients->integer; i++, cl++, gclient++) { if (cl->state < CS_CONNECTED) { continue; } if(gclient->sess.sessionTeam != TEAM_SPECTATOR) { continue; } ++numcl; XO("tr"); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", i);//CID XA(strbuf); XO("td");//Name XA(Webadmin_ConvertToHTMLColor(cl->name, colorbuf, sizeof(colorbuf))); XC; XO("td");//GUID if(cl->uid > 0) { XA(va("%d", cl->uid)); } else { if(showfullguid) XA(cl->pbguid); else XA(&cl->pbguid[24]); } XC; Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->power);//Ping XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", gclient->pers.scoreboard.score);//Score XA(strbuf); Com_sprintf(strbuf, sizeof(strbuf), "<td>%d</td>", cl->ping);//Ping XA(strbuf); XC; } XC; XA(va("%d players are on server", numcl)); }
/* <66b77> ../engine/net_chan.c:2067 */ NOXREF void Netchan_UpdateProgress(netchan_t *chan) { fragbuf_t *p; int c = 0; int total = 0; int i; float bestpercent = 0.0f; float percent; char sz[1024]; char *in; char *out; int len = 0; scr_downloading.value = -1.0f; gDownloadFile[0] = 0; if (net_drawslider.value != 1.0f) { if (!chan->incomingbufs[FRAG_FILE_STREAM]) return; } for (i = MAX_STREAMS - 1; i >= 0; i--) { if (chan->incomingbufs[i]) { p = chan->incomingbufs[i]; total = FRAG_GETCOUNT(p->bufferid); while (p) { c++; p = p->next; } if (total) { percent = (float)c * 100.0f / (float)total; if (percent > bestpercent) bestpercent = percent; } p = chan->incomingbufs[i]; if (i == FRAG_FILE_STREAM) { in = (char *)p->frag_message.data; out = sz; while (*in) { *out++ = *in++; len++; if (len > 128) break; } *out = '\0'; if (Q_strlen(sz) > 0 && (*sz != '!' || !Q_strncmp(sz, "!ModuleC.dll", 11))) { Q_strncpy(gDownloadFile, sz, 255); gDownloadFile[255] = 0; } } } else if (chan->fragbufs[i]) { if (chan->fragbufcount[i]) { percent = (float)chan->fragbufs[i]->bufferid * 100.0f / (float)chan->fragbufcount[i]; if (percent > bestpercent) bestpercent = percent; } } } scr_downloading.value = bestpercent; }
void Webadmin_BuildMessage(msg_t* msg, const char* username, qboolean invalidloginattempt, const char* banmsg, const char* url, httpPostVals_t* values) { xml_t xmlbase; xml_t* xmlobj = &xmlbase; char actionval[64]; char colorbuf[2048]; const char *postval; char netadrstr[128]; int uid; XML_Init(xmlobj, (char*)msg->data, msg->maxsize, "ISO-8859-1"); XO("html"); XO("head"); XO("title"); XA("CoD4X Web Server"); XC; XO2("link","href","/files/webadmin.css","rel","stylesheet"); XC; XC; XO("body"); XO1("div","class","container"); XO1("div","class","page-header"); XO("h1"); XA("CoD4 X v1.8"); XO("small"); XA(" Web Server"); XC; XC; XO("h3"); XA(Webadmin_ConvertToHTMLColor(sv_hostname->string, colorbuf, sizeof(colorbuf))); XA(" "); XA(sv_mapname->string); XC; XC; if(!Q_strncmp(url, "/webadmin", 9)) { if(username == NULL || username[0] == '\0') { Webadmin_BuildLoginForm(xmlobj, invalidloginattempt, banmsg); } else { if(!Q_strncmp(url +9, "/listadmins", 11)) { uid = Auth_GetUID(username); Webadmin_BuildAdminList(xmlobj, uid); } else { uid = Auth_GetUID(username); XO1("div","class","loginusername"); XO1("span","class","label label-primary"); XA("Logged in as: "); XA(username); XA(". "); XO2("a","href","/webadmin/?action=logout","style","color: #fff"); XA("Log Out"); XC; XC; XC; XO1("div", "class", "col-lg-6 right_line"); XO("h3"); XA("Server Status"); XC; XO("hr"); XC; Webadmin_BuildServerStatus(xmlobj, qtrue); XC; XO1("div", "class", "col-lg-6 left_line"); XO("h3"); XA("Command Console"); XC; XO("hr"); XC; if(Webadmin_GetUrlVal( url, "action", actionval, sizeof(actionval)))//nnjpls { if(strcmp(actionval, "sendcmd") == 0) { postval = Webadmin_GetPostVal(values, "consolecommand"); if(postval) { XO1("div","class","well"); Webadmin_ConsoleCommand(xmlobj, postval, uid); XC; } } else if (strcmp(actionval, "logout") == 0) { Auth_WipeSessionId(username); } else if(strcmp(actionval, "banclient") == 0) { Webadmin_BanClient(xmlobj, values, uid); } else if(strcmp(actionval, "kickclient") == 0) { Webadmin_KickClient(xmlobj, values, uid); } } XO5("form", "name", "input", "action", "webadmin?action=sendcmd", "method", "post", "class","form-control","id","con_form"); XA("<label for=\"consolecommand\">Send Command</label> <input type=\"text\" name=\"consolecommand\" id=\"consolecommand\">"); XA("<button class=\"givesomespace btn btn-primary btn-xs\" type=\"submit\">Send Command</button>"); XC; XC; } } } else if(!Q_strncmp(url, "/status", 7)) { XO("h3"); XA("Server Status"); XC; XO("hr"); XC; Webadmin_BuildServerStatus(xmlobj,qfalse); } else { XO1("h3","align","center"); XA("Where do you want to go?"); XC; XO1("div","align","center"); XA("<a href=\"/webadmin\" class=\"btn btn-primary givesomespace\">Web Admin</a>"); XA("<a href=\"/status\" class=\"btn btn-primary givesomespace\">Server Status</a>"); XC; } XO("p"); XA("Net: "); XA(NET_GetHostAddress(netadrstr, sizeof(netadrstr))); XC; XC; XC; XC; msg->cursize = xmlobj->bufposition; }
//----------------------------------------------------- static qboolean VEH_TurretFindEnemies( Vehicle_t *pVeh, gentity_t *parent, turretStats_t *turretStats, int turretNum, int curMuzzle ) //----------------------------------------------------- { qboolean found = qfalse; int i, count; float bestDist = turretStats->fAIRange * turretStats->fAIRange; float enemyDist; vec3_t enemyDir, org, org2; qboolean foundClient = qfalse; gentity_t *entity_list[MAX_GENTITIES], *target, *bestTarget = NULL; WP_CalcVehMuzzle( parent, curMuzzle ); VectorCopy( pVeh->m_vMuzzlePos[curMuzzle], org2 ); count = G_RadiusList( org2, turretStats->fAIRange, parent, qtrue, entity_list ); for ( i = 0; i < count; i++ ) { trace_t tr; target = entity_list[i]; if ( target == parent || !target->takedamage || target->health <= 0 || ( target->flags & FL_NOTARGET )) { continue; } if ( !target->client ) {// only attack clients if ( !(target->flags&FL_BBRUSH)//not a breakable brush || !target->takedamage//is a bbrush, but invincible || (target->NPC_targetname&&parent->targetname&&Q_stricmp(target->NPC_targetname,parent->targetname)!=0) )//not in invicible bbrush, but can only be broken by an NPC that is not me { if ( target->s.weapon == WP_TURRET && target->classname && Q_strncmp( "misc_turret", target->classname, 11 ) == 0 ) {//these guys we want to shoot at } else { continue; } } //else: we will shoot at bbrushes! } else if ( target->client->sess.sessionTeam == TEAM_SPECTATOR ) { continue; } if ( target == ((gentity_t*)pVeh->m_pPilot) || target->r.ownerNum == parent->s.number ) {//don't get angry at my pilot or passengers? continue; } if ( parent->client && parent->client->sess.sessionTeam ) { if ( target->client ) { if ( target->client->sess.sessionTeam == parent->client->sess.sessionTeam ) { // A bot/client/NPC we don't want to shoot continue; } } else if ( target->teamnodmg == parent->client->sess.sessionTeam ) {//some other entity that's allied with us continue; } } if ( !trap_InPVS( org2, target->r.currentOrigin )) { continue; } VectorCopy( target->r.currentOrigin, org ); trap_Trace( &tr, org2, NULL, NULL, org, parent->s.number, MASK_SHOT ); if ( tr.entityNum == target->s.number || (!tr.allsolid && !tr.startsolid && tr.fraction == 1.0 ) ) { // Only acquire if have a clear shot, Is it in range and closer than our best? VectorSubtract( target->r.currentOrigin, org2, enemyDir ); enemyDist = VectorLengthSquared( enemyDir ); if ( enemyDist < bestDist || (target->client && !foundClient))// all things equal, keep current { bestTarget = target; bestDist = enemyDist; found = qtrue; if ( target->client ) {//prefer clients over non-clients foundClient = qtrue; } } } } if ( found ) { pVeh->turretStatus[turretNum].enemyEntNum = bestTarget->s.number; } return found; }
qboolean HTTPCreateWebadminMessage(ftRequest_t* request, msg_t* msg, char* sessionkey, httpPostVals_t* values) { byte *buf; char qpath[MAX_QPATH]; int len; const char *session; char banmsg[1024]; buf = NULL; MSG_Init(msg, buf, 0); Com_Printf("URL: %s\n", request->url); if(!Q_strncmp(request->url, "/files", 6)) { if(request->url[6] != '/' || request->url[7] == '\0') { return qfalse; } Com_sprintf(qpath, sizeof(qpath), "/webadmindata/%s", &request->url[7]); if(strstr(qpath, "..") != NULL || strstr(qpath, "::") != NULL) { return qfalse; } len = FS_ReadFile(qpath, (void**)&buf); if(len < 0) { return qfalse; } msg->data = buf; msg->cursize = len; msg->maxsize = len; FS_FreeFileKeepBuf( ); return qtrue; } len = 0x20000; buf = Z_Malloc(len); if(buf == NULL) { return qfalse; } msg->data = buf; msg->cursize = 0; msg->maxsize = len; if (Q_stricmpn(request->url, "/webadmin", 9)) { Webadmin_BuildMessage(msg, NULL, qfalse, NULL ,request->url, values); return qtrue; } qboolean invalidlogin = qfalse; const char* username = NULL; const char* password = NULL; if(SV_PlayerBannedByip(&request->remote, banmsg, sizeof(banmsg))) { Webadmin_BuildMessage(msg, NULL, qfalse, banmsg, request->url, values); return qtrue; } username = Auth_FindSessionID(sessionkey); if(username == NULL) { username = Webadmin_GetPostVal(values, "username"); password = Webadmin_GetPostVal(values, "password"); if(username && password) { session = Auth_GetSessionId(username, password); if(session == NULL) { Com_Printf("^1Invalid login\n"); invalidlogin = qtrue; SV_PlayerAddBanByip(&request->remote, "Invalid login attempt. You have to wait 20 seconds", 0, NULL, 0, Com_GetRealtime() + 10); username = NULL; } else { Com_Printf("^2Successful login with username: %s\n", username); } } else { Com_Printf("No login!\n"); session = NULL; username = NULL; } /* not longer than 127 or overflow */ if(session != NULL) { strcpy(sessionkey, session); } } else { Com_Printf("Already logged in as: %s\n", username); } Webadmin_BuildMessage(msg, username, invalidlogin, NULL, request->url, values); return qtrue; }
void Sec_Update( qboolean getbasefiles ){ char buff[SEC_UPDATE_INITIALBUFFSIZE]; char *ptr,*ptr2, *testfile; char filepathbuf[MAX_OSPATH]; char baseurl[1024]; char name1[256],name2[256]; sec_file_t files, *currFile = &files; qboolean dlExec = qfalse; int len; char hash[128]; long unsigned size; ftRequest_t* filetransferobj; ftRequest_t* curfileobj; int transret; mvabuf; if(!Sec_Initialized()){ return; } #ifdef CAN_UPDATE Com_Printf("\n-----------------------------\n"); Com_Printf(" CoD4X Auto Update\n"); Com_Printf(" Current version: %g\n",SEC_VERSION); Com_Printf(" Current build: %d\n",BUILD_NUMBER); Com_Printf(" Current type: %s\n",SEC_TYPE == 's' ? "stable " : "experimental"); Com_Printf("-----------------------------\n\n"); canupdate = Cvar_RegisterBool("allowupdating", qtrue, 0, "This enables autoupdating of CoD4 server with new versions."); if(getbasefiles == qtrue) { Com_sprintf(buff, sizeof(buff), "http://" SEC_UPDATE_HOST SEC_UPDATE_GETGROUNDVERSION); }else{ if(canupdate->boolean == qfalse) return; Com_sprintf(buff, sizeof(buff), "http://" SEC_UPDATE_HOST SEC_UPDATE_GETVERSION); } #else if(getbasefiles == qtrue) { Com_sprintf(buff, sizeof(buff), "http://" SEC_UPDATE_HOST SEC_UPDATE_GETGROUNDVERSION); }else{ return; } #endif filetransferobj = FileDownloadRequest( buff ); if(filetransferobj == NULL){ return; } do { transret = FileDownloadSendReceive( filetransferobj ); usleep(20000); } while (transret == 0); if(transret < 0) { FileDownloadFreeRequest(filetransferobj); return; } /* Need to catch errors */ // FS_WriteFile("tmp.txt", va("%d", status), 1); // TODO: Do something with the status? // FS_WriteFile("tmp2.txt", packet.header, packet.headerLength); // FS_WriteFile("tmp3.txt", packet.content, packet.contentLength); if(filetransferobj->code <= 0){ Com_PrintError("Receiving data. Error code: %d.\n", filetransferobj->code); FileDownloadFreeRequest(filetransferobj); return; } if(filetransferobj->code == 204){ Com_Printf("\nServer is up to date.\n\n"); FileDownloadFreeRequest(filetransferobj); return; } else if(filetransferobj->code != 200){ Com_PrintWarning("The update server's malfunction.\nStatus code: %d.\n", filetransferobj->code); FileDownloadFreeRequest(filetransferobj); return; } Com_Memset(&files, 0, sizeof(files)); /* We need to parse filenames etc */ ptr = Sec_StrTok((char*)(filetransferobj->recvmsg.data + filetransferobj->headerLength),"\n",42); // Yes, 42. if(ptr == NULL || Q_stricmpn("baseurl: ", ptr, 9)) { Com_PrintWarning("Sec_Update: Corrupt data from update server. Update aborted.\n"); FileDownloadFreeRequest(filetransferobj); return; } Q_strncpyz(baseurl, ptr +9, sizeof(baseurl)); ptr = Sec_StrTok(NULL,"\n",42); // Yes, 42 again. while(ptr != NULL){ currFile->next = Sec_GMalloc(sec_file_t,1); currFile = currFile->next; Com_Memset(currFile,0,sizeof(sec_file_t)); ptr2 = strchr(ptr,' '); if(ptr2 == NULL){ Com_PrintWarning("Sec_Update: Corrupt data from update server. Update aborted.\nDebug:\"%s\"\n",ptr); FileDownloadFreeRequest(filetransferobj); return; } *ptr2++ = 0; Q_strncpyz(currFile->path,ptr,sizeof(currFile->path)); ptr = ptr2; ptr2 = strchr(ptr,' '); if(ptr2 == NULL){ Com_PrintWarning("Sec_Update: Corrupt data from update server. Update aborted.\nDebug:\"%s\"\n",ptr); FileDownloadFreeRequest(filetransferobj); return; } *ptr2++ = 0; if(!isInteger(ptr, 0)){ Com_PrintWarning("Sec_Update: Corrupt data from update server - size is not a number. Update aborted.\nDebug:\"%s\"\n",ptr); FileDownloadFreeRequest(filetransferobj); return; } currFile->size = atoi(ptr); Q_strncpyz(currFile->hash,ptr2,sizeof(currFile->hash)); Q_strncpyz(currFile->name,currFile->path, sizeof(currFile->name)); //printf("DEBUG: File to download: link: \"%s\", name: \"%s\", size: %d, hash: \"%s\"\n\n",file.path,file.name,file.size,file.hash); Com_sprintf(buff, sizeof(buff), SEC_UPDATE_DOWNLOAD(baseurl, currFile->path)); curfileobj = FileDownloadRequest(buff); if(curfileobj == NULL) { FileDownloadFreeRequest(filetransferobj); return; } Com_Printf("Downloading file: \"%s\"\n\n",currFile->name); do { transret = FileDownloadSendReceive( curfileobj ); Com_Printf("%s", FileDownloadGenerateProgress( curfileobj )); usleep(20000); } while (transret == 0); Com_Printf("\n"); if(transret < 0) { FileDownloadFreeRequest(curfileobj); FileDownloadFreeRequest(filetransferobj); return; } Q_strncpyz(buff,currFile->name, sizeof(buff)); Q_strcat(buff, sizeof(buff),".new"); if(curfileobj->code != 200){ Com_PrintError("Downloading has failed! Error code: %d. Update aborted.\n", curfileobj->code); FileDownloadFreeRequest(filetransferobj); FileDownloadFreeRequest(curfileobj); return; } len = FS_SV_BaseWriteFile(buff, curfileobj->recvmsg.data + curfileobj->headerLength, curfileobj->contentLength); if(len != curfileobj->contentLength){ len = FS_SV_HomeWriteFile(buff, curfileobj->recvmsg.data + curfileobj->headerLength, curfileobj->contentLength); if(len != curfileobj->contentLength) { Com_PrintError("Opening \"%s\" for writing! Update aborted.\n",buff); FileDownloadFreeRequest(filetransferobj); FileDownloadFreeRequest(curfileobj); return; } } ptr = Sec_StrTok(NULL,"\n",42); // Yes, 42 again. size = sizeof(hash); if(!Sec_HashMemory(SEC_HASH_SHA256, curfileobj->recvmsg.data + curfileobj->headerLength, curfileobj->contentLength, hash, &size,qfalse)){ Com_PrintError("Hashing the file \"%s\". Error code: %s.\nUpdate aborted.\n",currFile->name,Sec_CryptErrStr(SecCryptErr)); FileDownloadFreeRequest(filetransferobj); FileDownloadFreeRequest(curfileobj); return; } FileDownloadFreeRequest(curfileobj); if(!Q_strncmp(hash, currFile->hash, size)){ Com_Printf("Successfully downloaded file \"%s\".\n", currFile->name); } else{ Com_PrintError("File \"%s\" is corrupt!\nUpdate aborted.\n",currFile->name); Com_DPrintf("Hash: \"%s\", correct hash: \"%s\".\n",hash,currFile->hash); FileDownloadFreeRequest(filetransferobj); return; } } FileDownloadFreeRequest(filetransferobj); Com_Printf("All files downloaded successfully. Applying update...\n"); currFile = files.next; do{ Com_Printf("Updating file %s...\n", currFile->name); Q_strncpyz(name1, currFile->name, sizeof(name1)); Q_strcat(name1, sizeof(name1), ".old"); Q_strncpyz(name2, currFile->name, sizeof(name2)); Q_strcat(name2, sizeof(name2), ".new"); testfile = FS_SV_GetFilepath(name1, filepathbuf, sizeof(filepathbuf)); if(testfile != NULL) { // Old file exists, back it up FS_SV_BaseRemove( name1 ); FS_SV_HomeRemove( name1 ); testfile = FS_SV_GetFilepath(name1, filepathbuf, sizeof(filepathbuf)); if(testfile != NULL) { Com_PrintWarning("Couldn't remove backup file: %s\n", testfile); } if(FS_SV_HomeFileExists(name1) == qtrue) { Com_PrintError("Couldn't remove backup file from fs_homepath: %s\n", name1); } } // Check if an old file exists with this name testfile = FS_SV_GetFilepath(currFile->name, filepathbuf, sizeof(filepathbuf)); if(testfile != NULL) { // Old file exists, back it up FS_SV_Rename(currFile->name, name1); } testfile = FS_SV_GetFilepath(currFile->name, filepathbuf, sizeof(filepathbuf)); // We couldn't back it up. Now we try to just delete it. if(testfile != NULL) { FS_SV_BaseRemove( currFile->name ); FS_SV_HomeRemove( currFile->name ); testfile = FS_SV_GetFilepath( currFile->name, filepathbuf, sizeof(filepathbuf) ); if(testfile != NULL) { Com_PrintWarning("Couldn't remove file: %s\n", testfile); } if(FS_SV_HomeFileExists(currFile->name) == qtrue) { Com_PrintError("Couldn't remove file from fs_homepath: %s\n", currFile->name); Com_PrintError("Update has failed!\n"); return; } } if(Q_strncmp(currFile->name, EXECUTABLE_NAME, 15)){ /* This is not the executable file */ FS_SV_Rename(name2, currFile->name); testfile = FS_SV_GetFilepath(currFile->name, filepathbuf, sizeof(filepathbuf)); if(testfile == NULL) { Com_PrintError("Failed to rename file %s to %s\n", name2,currFile->name); Com_PrintError("Update has failed!\n"); return; } Com_Printf("Update on file %s successfully applied.\n",currFile->name); }else{ /* This is the executable file */ testfile = FS_SV_GetFilepath(name2, filepathbuf, sizeof(filepathbuf)); if(testfile == NULL) { Com_PrintError("Can not find file %s\n", name2); Com_PrintError("Update has failed!\n"); return; } if(FS_SetPermissionsExec(name2) == qfalse) { Com_PrintError("CRITICAL ERROR: failed to change mode of the file \"%s\"! Aborting, manual installation might be required.\n", name2); return; } FS_RenameOSPath(Sys_ExeFile(), va("%s.dead", Sys_ExeFile())); FS_RemoveOSPath(va("%s.dead", Sys_ExeFile())); FS_RemoveOSPath(Sys_ExeFile()); if(FS_FileExistsOSPath(Sys_ExeFile())) { Com_PrintError("Failed to delete file %s\n", Sys_ExeFile()); Com_PrintError("Update has failed!\n"); return; } FS_RenameOSPath(testfile, Sys_ExeFile()); if(!FS_FileExistsOSPath(Sys_ExeFile())) { Com_PrintError("Failed to rename file %s\n", testfile); Com_PrintError("Update has failed! Manual reinstallation of file %s is required. This server is now broken!\n", Sys_ExeFile()); return; } Com_Printf("Update on file %s successfully applied.\n", Sys_ExeFile()); dlExec = qtrue; } currFile = currFile->next; }while(currFile != NULL); Sec_FreeFileStruct(files.next); Com_Printf("Finalizing update...\n"); if(dlExec == qtrue) { Sys_Restart("System has been updated and will restart now."); }else{ FS_Restart( 0 ); } }
void CNB_Select_Level_Panel::UpdateLevelList() { const char *mapcfile = m_pMapListFile; // Check the time of the mapcycle file and re-populate the list of level names if the file has been modified const int nMapCycleTimeStamp = filesystem->GetPathTime( mapcfile, "GAME" ); char *szDefaultMapName = "sdk_teams_hdr"; if ( 0 == nMapCycleTimeStamp ) { // Map cycle file does not exist, make a list containing only the default map m_MapList.AddToTail( szDefaultMapName ); } else { // Clear out existing map list. Not using Purge() because I don't think that it will do a 'delete []' for ( int i = 0; i < m_MapList.Count(); i++ ) { delete [] m_MapList[i]; } m_MapList.RemoveAll(); // Repopulate map list from mapcycle file int nFileLength; char *aFileList = (char*)UTIL_LoadFileForMe( mapcfile, &nFileLength ); if ( aFileList && nFileLength ) { V_SplitString( aFileList, "\n", m_MapList ); for ( int i = 0; i < m_MapList.Count(); i++ ) { bool bIgnore = false; // Strip out the spaces in the name StripChar( m_MapList[i] , '\r'); StripChar( m_MapList[i] , ' '); /* if ( !engine->IsMapValid( m_MapList[i] ) ) { bIgnore = true; // If the engine doesn't consider it a valid map remove it from the lists char szWarningMessage[MAX_PATH]; V_snprintf( szWarningMessage, MAX_PATH, "Invalid map '%s' included in map cycle file. Ignored.\n", m_MapList[i] ); Warning( szWarningMessage ); } else */if ( !Q_strncmp( m_MapList[i], "//", 2 ) ) { bIgnore = true; } if ( bIgnore ) { delete [] m_MapList[i]; m_MapList.Remove( i ); --i; } } UTIL_FreeFile( (byte *)aFileList ); } // If somehow we have no maps in the list then add the default one if ( 0 == m_MapList.Count() ) { m_MapList.AddToTail( szDefaultMapName ); } // Now rebuild the level entry list //m_pHorizList->m_Entries.PurgeAndDeleteElements(); // Create entries for ( int i = 0; i < m_MapList.Count(); i++ ) { if ( m_pHorizList->m_Entries.Count() <= i ) { CNB_Select_Level_Entry *pEntry = new CNB_Select_Level_Entry( NULL, "Select_Level_Entry", m_MapList[i] ); m_pHorizList->AddEntry( pEntry ); } else { CNB_Select_Level_Entry *pEntry = dynamic_cast<CNB_Select_Level_Entry*>( m_pHorizList->m_Entries[i].Get() ); pEntry->SetMap( m_MapList[i] ); } } } }
/* ================= R_LoadIQM Load an IQM model and compute the joint matrices for every frame. ================= */ qboolean R_LoadIQM( model_t *mod, void *buffer, int filesize, const char *mod_name ) { iqmHeader_t *header; iqmVertexArray_t *vertexarray; iqmTriangle_t *triangle; iqmMesh_t *mesh; iqmJoint_t *joint; iqmPose_t *pose; iqmBounds_t *bounds; unsigned short *framedata; char *str; int i, j; float jointInvMats[IQM_MAX_JOINTS * 12] = {0.0f}; float *mat, *matInv; size_t size, joint_names; iqmData_t *iqmData; srfIQModel_t *surface; char meshName[MAX_QPATH]; byte blendIndexesType, blendWeightsType; if( filesize < sizeof(iqmHeader_t) ) { return qfalse; } header = (iqmHeader_t *)buffer; if( Q_strncmp( header->magic, IQM_MAGIC, sizeof(header->magic) ) ) { return qfalse; } LL( header->version ); if( header->version != IQM_VERSION ) { ri.Printf(PRINT_WARNING, "R_LoadIQM: %s is a unsupported IQM version (%d), only version %d is supported.\n", mod_name, header->version, IQM_VERSION); return qfalse; } LL( header->filesize ); if( header->filesize > filesize || header->filesize > 16<<20 ) { return qfalse; } LL( header->flags ); LL( header->num_text ); LL( header->ofs_text ); LL( header->num_meshes ); LL( header->ofs_meshes ); LL( header->num_vertexarrays ); LL( header->num_vertexes ); LL( header->ofs_vertexarrays ); LL( header->num_triangles ); LL( header->ofs_triangles ); LL( header->ofs_adjacency ); LL( header->num_joints ); LL( header->ofs_joints ); LL( header->num_poses ); LL( header->ofs_poses ); LL( header->num_anims ); LL( header->ofs_anims ); LL( header->num_frames ); LL( header->num_framechannels ); LL( header->ofs_frames ); LL( header->ofs_bounds ); LL( header->num_comment ); LL( header->ofs_comment ); LL( header->num_extensions ); LL( header->ofs_extensions ); // check ioq3 joint limit if ( header->num_joints > IQM_MAX_JOINTS ) { ri.Printf(PRINT_WARNING, "R_LoadIQM: %s has more than %d joints (%d).\n", mod_name, IQM_MAX_JOINTS, header->num_joints); return qfalse; } blendIndexesType = blendWeightsType = IQM_UBYTE; // check and swap vertex arrays if( IQM_CheckRange( header, header->ofs_vertexarrays, header->num_vertexarrays, sizeof(iqmVertexArray_t) ) ) { return qfalse; } vertexarray = (iqmVertexArray_t *)((byte *)header + header->ofs_vertexarrays); for( i = 0; i < header->num_vertexarrays; i++, vertexarray++ ) { int n, *intPtr; if( vertexarray->size <= 0 || vertexarray->size > 4 ) { return qfalse; } // total number of values n = header->num_vertexes * vertexarray->size; switch( vertexarray->format ) { case IQM_BYTE: case IQM_UBYTE: // 1 byte, no swapping necessary if( IQM_CheckRange( header, vertexarray->offset, n, sizeof(byte) ) ) { return qfalse; } break; case IQM_INT: case IQM_UINT: case IQM_FLOAT: // 4-byte swap if( IQM_CheckRange( header, vertexarray->offset, n, sizeof(float) ) ) { return qfalse; } intPtr = (int *)((byte *)header + vertexarray->offset); for( j = 0; j < n; j++, intPtr++ ) { LL( *intPtr ); } break; default: // not supported return qfalse; break; } switch( vertexarray->type ) { case IQM_POSITION: case IQM_NORMAL: if( vertexarray->format != IQM_FLOAT || vertexarray->size != 3 ) { return qfalse; } break; case IQM_TANGENT: if( vertexarray->format != IQM_FLOAT || vertexarray->size != 4 ) { return qfalse; } break; case IQM_TEXCOORD: if( vertexarray->format != IQM_FLOAT || vertexarray->size != 2 ) { return qfalse; } break; case IQM_BLENDINDEXES: if( (vertexarray->format != IQM_INT && vertexarray->format != IQM_UBYTE) || vertexarray->size != 4 ) { return qfalse; } blendIndexesType = vertexarray->format; break; case IQM_BLENDWEIGHTS: if( (vertexarray->format != IQM_FLOAT && vertexarray->format != IQM_UBYTE) || vertexarray->size != 4 ) { return qfalse; } blendWeightsType = vertexarray->format; break; case IQM_COLOR: if( vertexarray->format != IQM_UBYTE || vertexarray->size != 4 ) { return qfalse; } break; } } // check and swap triangles if( IQM_CheckRange( header, header->ofs_triangles, header->num_triangles, sizeof(iqmTriangle_t) ) ) { return qfalse; } triangle = (iqmTriangle_t *)((byte *)header + header->ofs_triangles); for( i = 0; i < header->num_triangles; i++, triangle++ ) { LL( triangle->vertex[0] ); LL( triangle->vertex[1] ); LL( triangle->vertex[2] ); if( triangle->vertex[0] > header->num_vertexes || triangle->vertex[1] > header->num_vertexes || triangle->vertex[2] > header->num_vertexes ) { return qfalse; } } // check and swap meshes if( IQM_CheckRange( header, header->ofs_meshes, header->num_meshes, sizeof(iqmMesh_t) ) ) { return qfalse; } mesh = (iqmMesh_t *)((byte *)header + header->ofs_meshes); for( i = 0; i < header->num_meshes; i++, mesh++) { LL( mesh->name ); LL( mesh->material ); LL( mesh->first_vertex ); LL( mesh->num_vertexes ); LL( mesh->first_triangle ); LL( mesh->num_triangles ); if ( mesh->name < header->num_text ) { Q_strncpyz( meshName, (char*)header + header->ofs_text + mesh->name, sizeof (meshName) ); } else { meshName[0] = '\0'; } // check ioq3 limits if ( mesh->num_vertexes >= SHADER_MAX_VERTEXES ) { ri.Printf(PRINT_WARNING, "R_LoadIQM: %s has more than %i verts on %s (%i).\n", mod_name, SHADER_MAX_VERTEXES - 1, meshName[0] ? meshName : "a surface", mesh->num_vertexes ); return qfalse; } if ( mesh->num_triangles*3 >= SHADER_MAX_INDEXES ) { ri.Printf(PRINT_WARNING, "R_LoadIQM: %s has more than %i triangles on %s (%i).\n", mod_name, ( SHADER_MAX_INDEXES / 3 ) - 1, meshName[0] ? meshName : "a surface", mesh->num_triangles ); return qfalse; } if( mesh->first_vertex >= header->num_vertexes || mesh->first_vertex + mesh->num_vertexes > header->num_vertexes || mesh->first_triangle >= header->num_triangles || mesh->first_triangle + mesh->num_triangles > header->num_triangles || mesh->name >= header->num_text || mesh->material >= header->num_text ) { return qfalse; } } if( header->num_poses != header->num_joints && header->num_poses != 0 ) { ri.Printf(PRINT_WARNING, "R_LoadIQM: %s has %d poses and %d joints, must have the same number or 0 poses\n", mod_name, header->num_poses, header->num_joints ); return qfalse; } joint_names = 0; if ( header->num_joints ) { // check and swap joints if( IQM_CheckRange( header, header->ofs_joints, header->num_joints, sizeof(iqmJoint_t) ) ) { return qfalse; } joint = (iqmJoint_t *)((byte *)header + header->ofs_joints); for( i = 0; i < header->num_joints; i++, joint++ ) { LL( joint->name ); LL( joint->parent ); LL( joint->translate[0] ); LL( joint->translate[1] ); LL( joint->translate[2] ); LL( joint->rotate[0] ); LL( joint->rotate[1] ); LL( joint->rotate[2] ); LL( joint->rotate[3] ); LL( joint->scale[0] ); LL( joint->scale[1] ); LL( joint->scale[2] ); if( joint->parent < -1 || joint->parent >= (int)header->num_joints || joint->name >= (int)header->num_text ) { return qfalse; } joint_names += strlen( (char *)header + header->ofs_text + joint->name ) + 1; } } if ( header->num_poses ) { // check and swap poses if( IQM_CheckRange( header, header->ofs_poses, header->num_poses, sizeof(iqmPose_t) ) ) { return qfalse; } pose = (iqmPose_t *)((byte *)header + header->ofs_poses); for( i = 0; i < header->num_poses; i++, pose++ ) { LL( pose->parent ); LL( pose->mask ); LL( pose->channeloffset[0] ); LL( pose->channeloffset[1] ); LL( pose->channeloffset[2] ); LL( pose->channeloffset[3] ); LL( pose->channeloffset[4] ); LL( pose->channeloffset[5] ); LL( pose->channeloffset[6] ); LL( pose->channeloffset[7] ); LL( pose->channeloffset[8] ); LL( pose->channeloffset[9] ); LL( pose->channelscale[0] ); LL( pose->channelscale[1] ); LL( pose->channelscale[2] ); LL( pose->channelscale[3] ); LL( pose->channelscale[4] ); LL( pose->channelscale[5] ); LL( pose->channelscale[6] ); LL( pose->channelscale[7] ); LL( pose->channelscale[8] ); LL( pose->channelscale[9] ); } } if (header->ofs_bounds) { // check and swap model bounds if(IQM_CheckRange(header, header->ofs_bounds, header->num_frames, sizeof(*bounds))) { return qfalse; } bounds = (iqmBounds_t *) ((byte *) header + header->ofs_bounds); for(i = 0; i < header->num_frames; i++) { LL(bounds->bbmin[0]); LL(bounds->bbmin[1]); LL(bounds->bbmin[2]); LL(bounds->bbmax[0]); LL(bounds->bbmax[1]); LL(bounds->bbmax[2]); bounds++; } } // allocate the model and copy the data size = sizeof(iqmData_t); size += header->num_meshes * sizeof( srfIQModel_t ); size += header->num_joints * 12 * sizeof( float ); // joint mats size += header->num_poses * header->num_frames * 12 * sizeof( float ); // pose mats if(header->ofs_bounds) size += header->num_frames * 6 * sizeof(float); // model bounds size += header->num_vertexes * 3 * sizeof(float); // positions size += header->num_vertexes * 2 * sizeof(float); // texcoords size += header->num_vertexes * 3 * sizeof(float); // normals size += header->num_vertexes * 4 * sizeof(float); // tangents size += header->num_vertexes * 4 * sizeof(byte); // blendIndexes size += header->num_vertexes * 4 * sizeof(byte); // colors size += header->num_joints * sizeof(int); // parents size += header->num_triangles * 3 * sizeof(int); // triangles size += joint_names; // joint names // blendWeights if (blendWeightsType == IQM_FLOAT) { size += header->num_vertexes * 4 * sizeof(float); } else { size += header->num_vertexes * 4 * sizeof(byte); } mod->type = MOD_IQM; iqmData = (iqmData_t *)ri.Hunk_Alloc( size, h_low ); mod->modelData = iqmData; // fill header iqmData->num_vertexes = header->num_vertexes; iqmData->num_triangles = header->num_triangles; iqmData->num_frames = header->num_frames; iqmData->num_surfaces = header->num_meshes; iqmData->num_joints = header->num_joints; iqmData->num_poses = header->num_poses; iqmData->blendWeightsType = blendWeightsType; iqmData->surfaces = (srfIQModel_t *)(iqmData + 1); iqmData->jointMats = (float *) (iqmData->surfaces + iqmData->num_surfaces); iqmData->poseMats = iqmData->jointMats + 12 * header->num_joints; if(header->ofs_bounds) { iqmData->bounds = iqmData->poseMats + 12 * header->num_poses * header->num_frames; iqmData->positions = iqmData->bounds + 6 * header->num_frames; } else iqmData->positions = iqmData->poseMats + 12 * header->num_poses * header->num_frames; iqmData->texcoords = iqmData->positions + 3 * header->num_vertexes; iqmData->normals = iqmData->texcoords + 2 * header->num_vertexes; iqmData->tangents = iqmData->normals + 3 * header->num_vertexes; iqmData->blendIndexes = (byte *)(iqmData->tangents + 4 * header->num_vertexes); if(blendWeightsType == IQM_FLOAT) { iqmData->blendWeights.f = (float *)(iqmData->blendIndexes + 4 * header->num_vertexes); iqmData->colors = (byte *)(iqmData->blendWeights.f + 4 * header->num_vertexes); } else { iqmData->blendWeights.b = iqmData->blendIndexes + 4 * header->num_vertexes; iqmData->colors = iqmData->blendWeights.b + 4 * header->num_vertexes; } iqmData->jointParents = (int *)(iqmData->colors + 4 * header->num_vertexes); iqmData->triangles = iqmData->jointParents + header->num_joints; iqmData->names = (char *)(iqmData->triangles + 3 * header->num_triangles); if ( header->num_joints == 0 ) iqmData->jointMats = NULL; if ( header->num_poses == 0 ) iqmData->poseMats = NULL; // calculate joint matrices and their inverses // joint inverses are needed only until the pose matrices are calculated mat = iqmData->jointMats; matInv = jointInvMats; joint = (iqmJoint_t *)((byte *)header + header->ofs_joints); for( i = 0; i < header->num_joints; i++, joint++ ) { float baseFrame[12], invBaseFrame[12]; JointToMatrix( joint->rotate, joint->scale, joint->translate, baseFrame ); Matrix34Invert( baseFrame, invBaseFrame ); if ( joint->parent >= 0 ) { Matrix34Multiply( iqmData->jointMats + 12 * joint->parent, baseFrame, mat ); mat += 12; Matrix34Multiply( invBaseFrame, jointInvMats + 12 * joint->parent, matInv ); matInv += 12; } else { Com_Memcpy( mat, baseFrame, sizeof(baseFrame) ); mat += 12; Com_Memcpy( matInv, invBaseFrame, sizeof(invBaseFrame) ); matInv += 12; } } // calculate pose matrices framedata = (unsigned short *)((byte *)header + header->ofs_frames); mat = iqmData->poseMats; for( i = 0; i < header->num_frames; i++ ) { pose = (iqmPose_t *)((byte *)header + header->ofs_poses); for( j = 0; j < header->num_poses; j++, pose++ ) { vec3_t translate; vec4_t rotate; vec3_t scale; float mat1[12], mat2[12]; translate[0] = pose->channeloffset[0]; if( pose->mask & 0x001) translate[0] += *framedata++ * pose->channelscale[0]; translate[1] = pose->channeloffset[1]; if( pose->mask & 0x002) translate[1] += *framedata++ * pose->channelscale[1]; translate[2] = pose->channeloffset[2]; if( pose->mask & 0x004) translate[2] += *framedata++ * pose->channelscale[2]; rotate[0] = pose->channeloffset[3]; if( pose->mask & 0x008) rotate[0] += *framedata++ * pose->channelscale[3]; rotate[1] = pose->channeloffset[4]; if( pose->mask & 0x010) rotate[1] += *framedata++ * pose->channelscale[4]; rotate[2] = pose->channeloffset[5]; if( pose->mask & 0x020) rotate[2] += *framedata++ * pose->channelscale[5]; rotate[3] = pose->channeloffset[6]; if( pose->mask & 0x040) rotate[3] += *framedata++ * pose->channelscale[6]; scale[0] = pose->channeloffset[7]; if( pose->mask & 0x080) scale[0] += *framedata++ * pose->channelscale[7]; scale[1] = pose->channeloffset[8]; if( pose->mask & 0x100) scale[1] += *framedata++ * pose->channelscale[8]; scale[2] = pose->channeloffset[9]; if( pose->mask & 0x200) scale[2] += *framedata++ * pose->channelscale[9]; // construct transformation matrix JointToMatrix( rotate, scale, translate, mat1 ); if( pose->parent >= 0 ) { Matrix34Multiply( iqmData->jointMats + 12 * pose->parent, mat1, mat2 ); } else { Com_Memcpy( mat2, mat1, sizeof(mat1) ); } Matrix34Multiply( mat2, jointInvMats + 12 * j, mat ); mat += 12; } } // register shaders // overwrite the material offset with the shader index mesh = (iqmMesh_t *)((byte *)header + header->ofs_meshes); surface = iqmData->surfaces; str = (char *)header + header->ofs_text; for( i = 0; i < header->num_meshes; i++, mesh++, surface++ ) { surface->surfaceType = SF_IQM; Q_strncpyz(surface->name, str + mesh->name, sizeof (surface->name)); Q_strlwr(surface->name); // lowercase the surface name so skin compares are faster surface->shader = R_FindShader( str + mesh->material, LIGHTMAP_NONE, qtrue ); if( surface->shader->defaultShader ) surface->shader = tr.defaultShader; surface->data = iqmData; surface->first_vertex = mesh->first_vertex; surface->num_vertexes = mesh->num_vertexes; surface->first_triangle = mesh->first_triangle; surface->num_triangles = mesh->num_triangles; } // copy vertexarrays and indexes vertexarray = (iqmVertexArray_t *)((byte *)header + header->ofs_vertexarrays); for( i = 0; i < header->num_vertexarrays; i++, vertexarray++ ) { int n; // total number of values n = header->num_vertexes * vertexarray->size; switch( vertexarray->type ) { case IQM_POSITION: Com_Memcpy( iqmData->positions, (byte *)header + vertexarray->offset, n * sizeof(float) ); break; case IQM_NORMAL: Com_Memcpy( iqmData->normals, (byte *)header + vertexarray->offset, n * sizeof(float) ); break; case IQM_TANGENT: Com_Memcpy( iqmData->tangents, (byte *)header + vertexarray->offset, n * sizeof(float) ); break; case IQM_TEXCOORD: Com_Memcpy( iqmData->texcoords, (byte *)header + vertexarray->offset, n * sizeof(float) ); break; case IQM_BLENDINDEXES: if( blendIndexesType == IQM_INT ) { int *data = (int*)((byte*)header + vertexarray->offset); for ( j = 0; j < n; j++ ) { iqmData->blendIndexes[j] = (byte)data[j]; } } else { Com_Memcpy( iqmData->blendIndexes, (byte *)header + vertexarray->offset, n * sizeof(byte) ); } break; case IQM_BLENDWEIGHTS: if( blendWeightsType == IQM_FLOAT ) { Com_Memcpy( iqmData->blendWeights.f, (byte *)header + vertexarray->offset, n * sizeof(float) ); } else { Com_Memcpy( iqmData->blendWeights.b, (byte *)header + vertexarray->offset, n * sizeof(byte) ); } break; case IQM_COLOR: Com_Memcpy( iqmData->colors, (byte *)header + vertexarray->offset, n * sizeof(byte) ); break; } } // copy joint parents joint = (iqmJoint_t *)((byte *)header + header->ofs_joints); for( i = 0; i < header->num_joints; i++, joint++ ) { iqmData->jointParents[i] = joint->parent; } // copy triangles triangle = (iqmTriangle_t *)((byte *)header + header->ofs_triangles); for( i = 0; i < header->num_triangles; i++, triangle++ ) { iqmData->triangles[3*i+0] = triangle->vertex[0]; iqmData->triangles[3*i+1] = triangle->vertex[1]; iqmData->triangles[3*i+2] = triangle->vertex[2]; } // copy joint names str = iqmData->names; joint = (iqmJoint_t *)((byte *)header + header->ofs_joints); for( i = 0; i < header->num_joints; i++, joint++ ) { char *name = (char *)header + header->ofs_text + joint->name; int len = strlen( name ) + 1; Com_Memcpy( str, name, len ); str += len; } // copy model bounds if(header->ofs_bounds) { mat = iqmData->bounds; bounds = (iqmBounds_t *) ((byte *) header + header->ofs_bounds); for(i = 0; i < header->num_frames; i++) { mat[0] = bounds->bbmin[0]; mat[1] = bounds->bbmin[1]; mat[2] = bounds->bbmin[2]; mat[3] = bounds->bbmax[0]; mat[4] = bounds->bbmax[1]; mat[5] = bounds->bbmax[2]; mat += 6; bounds++; } } return qtrue; }
//----------------------------------------------------------------------------- // // Look for vgui screens, returns true if it found one ... // //----------------------------------------------------------------------------- C_BaseEntity *FindNearbyVguiScreen( const Vector &viewPosition, const QAngle &viewAngle, int nTeam ) { if ( IsX360() ) { // X360TBD: Turn this on if feature actually used return NULL; } C_BasePlayer *pLocalPlayer = C_BasePlayer::GetLocalPlayer(); Assert( pLocalPlayer ); if ( !pLocalPlayer ) return NULL; // Get the view direction... Vector lookDir; AngleVectors( viewAngle, &lookDir ); // Create a ray used for raytracing Vector lookEnd; VectorMA( viewPosition, 2.0f * VGUI_SCREEN_MODE_RADIUS, lookDir, lookEnd ); Ray_t lookRay; lookRay.Init( viewPosition, lookEnd ); #ifndef C17 // Look for vgui screens that are close to the player CVGuiScreenEnumerator localScreens; partition->EnumerateElementsInSphere( PARTITION_CLIENT_NON_STATIC_EDICTS, viewPosition, VGUI_SCREEN_MODE_RADIUS, false, &localScreens ); #endif Vector vecOut, vecViewDelta; float flBestDist = 2.0f; C_VGuiScreen *pBestScreen = NULL; #ifdef C17 for (int i = 0; i < g_pVGUIScreens.Count(); i++) { if (g_pVGUIScreens.IsValidIndex(i)) { C_VGuiScreen *pScreen = g_pVGUIScreens[i]; #else for (int i = localScreens.GetScreenCount(); --i >= 0; ) { C_VGuiScreen *pScreen = localScreens.GetVGuiScreen(i); #endif if (pScreen->IsAttachedToViewModel()) continue; // Don't bother with screens I'm behind... // Hax - don't cancel backfacing with viewmodel attached screens. // we can get prediction bugs that make us backfacing for one frame and // it resets the mouse position if we lose focus. if (pScreen->IsBackfacing(viewPosition)) continue; // Don't bother with screens that are turned off if (!pScreen->IsActive()) continue; // FIXME: Should this maybe go into a derived class of some sort? // Don't bother with screens on the wrong team if (!pScreen->IsVisibleToTeam(nTeam)) continue; if (!pScreen->AcceptsInput()) continue; if (pScreen->IsInputOnlyToOwner() && pScreen->GetPlayerOwner() != pLocalPlayer) continue; // Test perpendicular distance from the screen... pScreen->GetVectors(NULL, NULL, &vecOut); VectorSubtract(viewPosition, pScreen->GetAbsOrigin(), vecViewDelta); float flPerpDist = DotProduct(vecViewDelta, vecOut); if ((flPerpDist < 0) || (flPerpDist > VGUI_SCREEN_MODE_RADIUS)) continue; // Perform a raycast to see where in barycentric coordinates the ray hits // the viewscreen; if it doesn't hit it, you're not in the mode float u, v, t; if (!pScreen->IntersectWithRay(lookRay, &u, &v, &t)) continue; // Barycentric test if ((u < 0) || (v < 0) || (u > 1) || (v > 1)) continue; if (t < flBestDist) { flBestDist = t; pBestScreen = pScreen; } } #ifdef C17 } #endif return pBestScreen; } void ActivateVguiScreen( C_BaseEntity *pVguiScreenEnt ) { if (pVguiScreenEnt) { Assert( dynamic_cast<C_VGuiScreen*>(pVguiScreenEnt) ); C_VGuiScreen *pVguiScreen = static_cast<C_VGuiScreen*>(pVguiScreenEnt); pVguiScreen->GainFocus( ); } } void SetVGuiScreenButtonState( C_BaseEntity *pVguiScreenEnt, int nButtonState ) { if (pVguiScreenEnt) { Assert( dynamic_cast<C_VGuiScreen*>(pVguiScreenEnt) ); C_VGuiScreen *pVguiScreen = static_cast<C_VGuiScreen*>(pVguiScreenEnt); pVguiScreen->SetButtonState( nButtonState ); } } void DeactivateVguiScreen( C_BaseEntity *pVguiScreenEnt ) { if (pVguiScreenEnt) { Assert( dynamic_cast<C_VGuiScreen*>(pVguiScreenEnt) ); C_VGuiScreen *pVguiScreen = static_cast<C_VGuiScreen*>(pVguiScreenEnt); pVguiScreen->LoseFocus( ); } } CVGuiScreenPanel::CVGuiScreenPanel( vgui::Panel *parent, const char *panelName ) : BaseClass( parent, panelName ) { m_hEntity = NULL; } CVGuiScreenPanel::CVGuiScreenPanel( vgui::Panel *parent, const char *panelName, vgui::HScheme hScheme ) : BaseClass( parent, panelName, hScheme ) { m_hEntity = NULL; } bool CVGuiScreenPanel::Init( KeyValues* pKeyValues, VGuiScreenInitData_t* pInitData ) { const char *pResFile = pKeyValues->GetString( "resfile" ); if (pResFile[0] != 0) { KeyValues *pCachedKeyValues = CacheKeyValuesForFile( pResFile ); LoadControlSettings( pResFile, NULL, pCachedKeyValues ); } // Dimensions in pixels int nWidth, nHeight; nWidth = pKeyValues->GetInt( "pixelswide", 240 ); nHeight = pKeyValues->GetInt( "pixelshigh", 160 ); if ((nWidth <= 0) || (nHeight <= 0)) return false; // If init data isn't specified, then we're just precaching. if ( pInitData ) { m_hEntity.Set( pInitData->m_pEntity ); C_VGuiScreen *screen = dynamic_cast< C_VGuiScreen * >( pInitData->m_pEntity ); if ( screen ) { bool acceptsInput = pKeyValues->GetInt( "acceptsinput", 1 ) ? true : false; screen->SetAcceptsInput( acceptsInput ); } } SetBounds( 0, 0, nWidth, nHeight ); return true; } vgui::Panel *CVGuiScreenPanel::CreateControlByName(const char *controlName) { // Check the panel metaclass manager to make these controls... if (!Q_strncmp(controlName, "MaterialImage", 20)) { return new CBitmapPanel(NULL, "BitmapPanel"); } if (!Q_strncmp(controlName, "MaterialButton", 20)) { return new CBitmapButton(NULL, "BitmapButton", ""); } // Didn't find it? Just use the default stuff return BaseClass::CreateControlByName( controlName ); } //----------------------------------------------------------------------------- // Purpose: Called when the user presses a button //----------------------------------------------------------------------------- void CVGuiScreenPanel::OnCommand( const char *command) { if ( Q_stricmp( command, "vguicancel" ) ) { engine->ClientCmd( const_cast<char *>( command ) ); } BaseClass::OnCommand(command); } DECLARE_VGUI_SCREEN_FACTORY( CVGuiScreenPanel, "vgui_screen_panel" );
bool CSDKPlayer::ClientCommand( const CCommand &args ) { const char *pcmd = args[0]; if ( FStrEq( pcmd, "jointeam" ) ) { if ( args.ArgC() < 2 ) { Warning( "Player sent bad jointeam syntax\n" ); } int iTeam = atoi( args[1] ); HandleCommand_JoinTeam( iTeam ); return true; } else if( !Q_strncmp( pcmd, "cls_", 4 ) ) { #if defined ( SDK_USE_PLAYERCLASSES ) CSDKTeam *pTeam = GetGlobalSDKTeam( GetTeamNumber() ); Assert( pTeam ); int iClassIndex = PLAYERCLASS_UNDEFINED; if( pTeam->IsClassOnTeam( pcmd, iClassIndex ) ) { HandleCommand_JoinClass( iClassIndex ); } else { DevMsg( "player tried to join a class that isn't on this team ( %s )\n", pcmd ); ShowClassSelectMenu(); } #endif return true; } else if ( FStrEq( pcmd, "spectate" ) ) { // instantly join spectators HandleCommand_JoinTeam( TEAM_SPECTATOR ); return true; } else if ( FStrEq( pcmd, "joingame" ) ) { // player just closed MOTD dialog if ( m_iPlayerState == STATE_WELCOME ) { //Tony; using teams, go to picking team. #if defined( SDK_USE_TEAMS ) State_Transition( STATE_PICKINGTEAM ); //Tony; not using teams, but we are using classes, so go straight to class picking. #elif !defined ( SDK_USE_TEAMS ) && defined ( SDK_USE_PLAYERCLASSES ) State_Transition( STATE_PICKINGCLASS ); //Tony; not using teams or classes, go straight to active. #else State_Transition( STATE_ACTIVE ); #endif } return true; } else if ( FStrEq( pcmd, "joinclass" ) ) { #if defined ( SDK_USE_PLAYERCLASSES ) if ( args.ArgC() < 2 ) { Warning( "Player sent bad joinclass syntax\n" ); } int iClass = atoi( args[1] ); HandleCommand_JoinClass( iClass ); #endif return true; } else if ( FStrEq( pcmd, "menuopen" ) ) { #if defined ( SDK_USE_PLAYERCLASSES ) SetClassMenuOpen( true ); #endif return true; } else if ( FStrEq( pcmd, "menuclosed" ) ) { #if defined ( SDK_USE_PLAYERCLASSES ) SetClassMenuOpen( false ); #endif return true; } else if ( FStrEq( pcmd, "droptest" ) ) { ThrowActiveWeapon(); return true; } return BaseClass::ClientCommand( args ); }
//----------------------------------------------------------------------------- // Does the next bytes of the buffer match a pattern? //----------------------------------------------------------------------------- bool CUtlBuffer::PeekStringMatch( int nOffset, const char *pString, int nLen ) { if ( !CheckPeekGet( nOffset, nLen ) ) return false; return !Q_strncmp( (const char*)PeekGet(nOffset), pString, nLen ); }
/* ================= Mod_LoadTextures ================= */ void Mod_LoadTextures (lump_t *l) { int i, j, pixels, num, max, altmax; miptex_t *mt; texture_t *tx, *tx2; texture_t *anims[10]; texture_t *altanims[10]; dmiptexlump_t *m; if (!l->filelen) { loadmodel->textures = NULL; return; } m = (dmiptexlump_t *)(mod_base + l->fileofs); m->nummiptex = LittleLong (m->nummiptex); loadmodel->numtextures = m->nummiptex; loadmodel->textures = Hunk_AllocName (m->nummiptex * sizeof(*loadmodel->textures) , loadname); for (i=0 ; i<m->nummiptex ; i++) { m->dataofs[i] = LittleLong(m->dataofs[i]); if (m->dataofs[i] == -1) continue; mt = (miptex_t *)((byte *)m + m->dataofs[i]); mt->width = LittleLong (mt->width); mt->height = LittleLong (mt->height); for (j=0 ; j<MIPLEVELS ; j++) mt->offsets[j] = LittleLong (mt->offsets[j]); if ( (mt->width & 15) || (mt->height & 15) ) Sys_Error ("Texture %s is not 16 aligned", mt->name); pixels = mt->width*mt->height/64*85; tx = Hunk_AllocName (sizeof(texture_t) +pixels, loadname ); loadmodel->textures[i] = tx; memcpy (tx->name, mt->name, sizeof(tx->name)); tx->width = mt->width; tx->height = mt->height; for (j=0 ; j<MIPLEVELS ; j++) tx->offsets[j] = mt->offsets[j] + sizeof(texture_t) - sizeof(miptex_t); // the pixels immediately follow the structures memcpy ( tx+1, mt+1, pixels); if (!Q_strncmp(mt->name,"sky",3)) R_InitSky (tx); } // // sequence the animations // for (i=0 ; i<m->nummiptex ; i++) { tx = loadmodel->textures[i]; if (!tx || tx->name[0] != '+') continue; if (tx->anim_next) continue; // allready sequenced // find the number of frames in the animation memset (anims, 0, sizeof(anims)); memset (altanims, 0, sizeof(altanims)); max = tx->name[1]; altmax = 0; if (max >= 'a' && max <= 'z') max -= 'a' - 'A'; if (max >= '0' && max <= '9') { max -= '0'; altmax = 0; anims[max] = tx; max++; } else if (max >= 'A' && max <= 'J') { altmax = max - 'A'; max = 0; altanims[altmax] = tx; altmax++; } else Sys_Error ("Bad animating texture %s", tx->name); for (j=i+1 ; j<m->nummiptex ; j++) { tx2 = loadmodel->textures[j]; if (!tx2 || tx2->name[0] != '+') continue; if (strcmp (tx2->name+2, tx->name+2)) continue; num = tx2->name[1]; if (num >= 'a' && num <= 'z') num -= 'a' - 'A'; if (num >= '0' && num <= '9') { num -= '0'; anims[num] = tx2; if (num+1 > max) max = num + 1; } else if (num >= 'A' && num <= 'J') { num = num - 'A'; altanims[num] = tx2; if (num+1 > altmax) altmax = num+1; } else Sys_Error ("Bad animating texture %s", tx->name); } #define ANIM_CYCLE 2 // link them all together for (j=0 ; j<max ; j++) { tx2 = anims[j]; if (!tx2) Sys_Error ("Missing frame %i of %s",j, tx->name); tx2->anim_total = max * ANIM_CYCLE; tx2->anim_min = j * ANIM_CYCLE; tx2->anim_max = (j+1) * ANIM_CYCLE; tx2->anim_next = anims[ (j+1)%max ]; if (altmax) tx2->alternate_anims = altanims[0]; } for (j=0 ; j<altmax ; j++) { tx2 = altanims[j]; if (!tx2) Sys_Error ("Missing frame %i of %s",j, tx->name); tx2->anim_total = altmax * ANIM_CYCLE; tx2->anim_min = j * ANIM_CYCLE; tx2->anim_max = (j+1) * ANIM_CYCLE; tx2->anim_next = altanims[ (j+1)%altmax ]; if (max) tx2->alternate_anims = anims[0]; } } }
/* ============ AnimParseAnimConfig returns qfalse if error, qtrue otherwise ============ */ static qboolean AnimParseAnimConfig( playerInfo_t *animModelInfo, const char *filename, const char *input ) { char *text_p, *token; animation_t *animations; headAnimation_t *headAnims; int i, fps, skip=-1; // if (!weaponStringsInited) { // BG_InitWeaponStrings(); // } // globalFilename = (char *)filename; animations = animModelInfo->animations; animModelInfo->numAnimations = 0; // headAnims = animModelInfo->headAnims; text_p = (char *)input; COM_BeginParseSession("AnimParseAnimConfig"); animModelInfo->footsteps = FOOTSTEP_NORMAL; VectorClear( animModelInfo->headOffset ); animModelInfo->gender = GENDER_MALE; animModelInfo->isSkeletal = qfalse; animModelInfo->version = 0; // read optional parameters while ( 1 ) { token = COM_Parse( &text_p ); if ( !token ) { break; } if ( !Q_stricmp( token, "footsteps" ) ) { token = COM_Parse( &text_p ); if ( !token ) { break; } if ( !Q_stricmp( token, "default" ) || !Q_stricmp( token, "normal" ) ) { animModelInfo->footsteps = FOOTSTEP_NORMAL; } else if ( !Q_stricmp( token, "boot" ) ) { animModelInfo->footsteps = FOOTSTEP_BOOT; } else if ( !Q_stricmp( token, "flesh" ) ) { animModelInfo->footsteps = FOOTSTEP_FLESH; } else if ( !Q_stricmp( token, "mech" ) ) { animModelInfo->footsteps = FOOTSTEP_MECH; } else if ( !Q_stricmp( token, "energy" ) ) { animModelInfo->footsteps = FOOTSTEP_ENERGY; } else { // BG_AnimParseError( "Bad footsteps parm '%s'\n", token ); } continue; } else if ( !Q_stricmp( token, "headoffset" ) ) { for ( i = 0 ; i < 3 ; i++ ) { token = COM_Parse( &text_p ); if ( !token ) { break; } animModelInfo->headOffset[i] = atof( token ); } continue; } else if ( !Q_stricmp( token, "sex" ) ) { token = COM_Parse( &text_p ); if ( !token ) { break; } if ( token[0] == 'f' || token[0] == 'F' ) { animModelInfo->gender = GENDER_FEMALE; } else if ( token[0] == 'n' || token[0] == 'N' ) { animModelInfo->gender = GENDER_NEUTER; } else { animModelInfo->gender = GENDER_MALE; } continue; } else if ( !Q_stricmp( token, "version" ) ) { token = COM_Parse( &text_p ); if ( !token ) { break; } animModelInfo->version = atoi(token); continue; } else if ( !Q_stricmp( token, "skeletal" ) ) { animModelInfo->isSkeletal = qtrue; continue; } if (animModelInfo->version < 2) { // if it is a number, start parsing animations if ( token[0] >= '0' && token[0] <= '9' ) { text_p -= strlen(token); // unget the token break; } } // STARTANIMS marks the start of the animations if ( !Q_stricmp( token, "STARTANIMS" ) ) { break; } // BG_AnimParseError( "unknown token '%s'", token ); } // read information for each frame for ( i = 0 ; (animModelInfo->version > 1) || (i < MAX_ANIMATIONS) ; i++ ) { token = COM_Parse( &text_p ); if ( !token ) { break; } if (animModelInfo->version > 1) { // includes animation names at start of each line if (!Q_stricmp( token, "ENDANIMS" )) { // end of animations break; } Q_strncpyz( animations[i].name, token, sizeof(animations[i].name) ); // convert to all lower case Q_strlwr( animations[i].name ); // token = COM_ParseExt( &text_p, qfalse ); if ( !token || !token[0] ) { // BG_AnimParseError( "end of file without ENDANIMS" ); } } else { // just set it to the equivalent animStrings[] Q_strncpyz( animations[i].name, animStrings[i], sizeof(animations[i].name) ); // convert to all lower case Q_strlwr( animations[i].name ); } animations[i].firstFrame = atoi( token ); if ( !animModelInfo->isSkeletal ) { // skeletal models dont require adjustment // leg only frames are adjusted to not count the upper body only frames if ( i == LEGS_WALKCR ) { skip = animations[LEGS_WALKCR].firstFrame - animations[TORSO_GESTURE].firstFrame; } if ( i >= LEGS_WALKCR ) { animations[i].firstFrame -= skip; } } token = COM_ParseExt( &text_p, qfalse ); if ( !token || !token[0] ) { // BG_AnimParseError( "end of file without ENDANIMS" ); } animations[i].numFrames = atoi( token ); token = COM_ParseExt( &text_p, qfalse ); if ( !token || !token[0] ) { // BG_AnimParseError( "end of file without ENDANIMS: line %i" ); } animations[i].loopFrames = atoi( token ); token = COM_ParseExt( &text_p, qfalse ); if ( !token || !token[0] ) { // BG_AnimParseError( "end of file without ENDANIMS: line %i" ); } fps = atof( token ); if ( fps == 0 ) { fps = 1; } animations[i].frameLerp = 1000 / fps; animations[i].initialLerp = 1000 / fps; // movespeed token = COM_ParseExt( &text_p, qfalse ); if ( !token || !token[0] ) { // BG_AnimParseError( "end of file without ENDANIMS" ); } animations[i].moveSpeed = atoi( token ); // animation blending token = COM_ParseExt( &text_p, qfalse ); // must be on same line if ( !token ) { animations[i].animBlend = 0; } else { animations[i].animBlend = atoi( token ); } // calculate the duration animations[i].duration = animations[i].initialLerp + animations[i].frameLerp * animations[i].numFrames + animations[i].animBlend; // get the nameHash animations[i].nameHash = BG_StringHashValue( animations[i].name ); if (!Q_strncmp(animations[i].name, "climb", 5)) { animations[i].flags |= ANIMFL_LADDERANIM; } if (strstr(animations[i].name, "firing")) { animations[i].flags |= ANIMFL_FIRINGANIM; animations[i].initialLerp = 40; } } animModelInfo->numAnimations = i; if ( animModelInfo->version < 2 && i != MAX_ANIMATIONS ) { // BG_AnimParseError( "Incorrect number of animations" ); return qfalse; } return qtrue; // NERVE - SMF - blah // check for head anims token = COM_Parse( &text_p ); if (token && token[0]) { if (animModelInfo->version < 2 || !Q_stricmp( token, "HEADFRAMES" )) { // read information for each head frame for ( i = 0 ; i < MAX_HEAD_ANIMS ; i++ ) { token = COM_Parse( &text_p ); if ( !token || !token[0] ) { break; } if (animModelInfo->version > 1) { // includes animation names at start of each line // just throw this information away, not required for head token = COM_ParseExt( &text_p, qfalse ); if ( !token || !token[0] ) { break; } } if (!i) { skip = atoi( token ); } headAnims[i].firstFrame = atoi( token ); // modify according to last frame of the main animations, since the head is totally seperate headAnims[i].firstFrame -= animations[MAX_ANIMATIONS-1].firstFrame + animations[MAX_ANIMATIONS-1].numFrames + skip; token = COM_ParseExt( &text_p, qfalse ); if ( !token || !token[0] ) { break; } headAnims[i].numFrames = atoi( token ); // skip the movespeed token = COM_ParseExt( &text_p, qfalse ); } // animModelInfo->numHeadAnims = i; if ( i != MAX_HEAD_ANIMS ) { // BG_AnimParseError( "Incorrect number of head frames" ); return qfalse; } } } return qtrue; }
static animation_t * BG_RAG_FindFreeAnimation(const char *mdxFileName, const char *name) #endif // CGAMEDLL { int i; for (i = 0; i < MAX_ANIMPOOL_SIZE; i++) { #ifdef USE_MDXFILE if (animationPool[i].mdxFile == mdxFile && !Q_stricmp(animationPool[i].name, name)) { #else if (*animationPool[i].mdxFileName && !Q_stricmp(animationPool[i].mdxFileName, mdxFileName) && !Q_stricmp(animationPool[i].name, name)) { #endif // CGAMEDLL return(&animationPool[i]); } } for (i = 0; i < MAX_ANIMPOOL_SIZE; i++) { #ifdef USE_MDXFILE if (!animationPool[i].mdxFile) { animationPool[i].mdxFile = mdxFile; #else if (!animationPool[i].mdxFileName[0]) { Q_strncpyz(animationPool[i].mdxFileName, mdxFileName, sizeof(animationPool[i].mdxFileName)); #endif // CGAMEDLL Q_strncpyz(animationPool[i].name, name, sizeof(animationPool[i].name)); return(&animationPool[i]); } } return NULL; } /** * @brief BG_RAG_ParseError * @param[in] handle * @param[in] format * @return */ static qboolean BG_RAG_ParseError(int handle, const char *format, ...) { int line; char filename[MAX_QPATH]; va_list argptr; static char string[4096]; va_start(argptr, format); Q_vsnprintf(string, sizeof(string), format, argptr); va_end(argptr); filename[0] = '\0'; line = 0; trap_PC_SourceFileAndLine(handle, filename, &line); Com_Printf(S_COLOR_RED "ERROR: %s, line %d: %s\n", filename, line, string); trap_PC_FreeSource(handle); return qfalse; } /** * @brief BG_RAG_ParseAnimation * @param[in] handle * @param[in,out] animation * @return */ static qboolean BG_RAG_ParseAnimation(int handle, animation_t *animation) { int i; animation->flags = 0; if (!PC_Int_Parse(handle, &animation->firstFrame)) { return BG_RAG_ParseError(handle, "expected first frame integer"); } if (!PC_Int_Parse(handle, &animation->numFrames)) { return BG_RAG_ParseError(handle, "expected length integer"); } if (!PC_Int_Parse(handle, &animation->loopFrames)) { return BG_RAG_ParseError(handle, "expected looping integer"); } if (!PC_Int_Parse(handle, &i)) { return BG_RAG_ParseError(handle, "expected fps integer"); } if (i == 0) { i = 1; } animation->frameLerp = (int)(1000 / (float)i); animation->initialLerp = (int)(1000 / (float)i); if (!PC_Int_Parse(handle, &animation->moveSpeed)) { return BG_RAG_ParseError(handle, "expected move speed integer"); } if (!PC_Int_Parse(handle, &animation->animBlend)) { return BG_RAG_ParseError(handle, "expected transition integer"); } if (!PC_Int_Parse(handle, &i)) { return BG_RAG_ParseError(handle, "expected reversed integer"); } if (i == 1) { animation->flags |= ANIMFL_REVERSED; } // calculate the duration animation->duration = animation->initialLerp + animation->frameLerp * animation->numFrames + animation->animBlend; // get the nameHash animation->nameHash = BG_StringHashValue(animation->name); // hacky-ish stuff if (!Q_strncmp(animation->name, "climb", 5)) { animation->flags |= ANIMFL_LADDERANIM; } if (strstr(animation->name, "firing")) { animation->flags |= ANIMFL_FIRINGANIM; animation->initialLerp = 40; } return qtrue; }
/* ================= main ================= */ int main( int argc, char **argv ) { int i; char commandLine[ MAX_STRING_CHARS ] = { 0 }; #ifndef DEDICATED // SDL version check // Compile time # if !SDL_VERSION_ATLEAST(MINSDL_MAJOR,MINSDL_MINOR,MINSDL_PATCH) # error A more recent version of SDL is required # endif // Run time SDL_version ver; SDL_GetVersion( &ver ); #define MINSDL_VERSION \ XSTRING(MINSDL_MAJOR) "." \ XSTRING(MINSDL_MINOR) "." \ XSTRING(MINSDL_PATCH) if( SDL_VERSIONNUM( ver.major, ver.minor, ver.patch ) < SDL_VERSIONNUM( MINSDL_MAJOR, MINSDL_MINOR, MINSDL_PATCH ) ) { Sys_Dialog( DT_ERROR, va( "SDL version " MINSDL_VERSION " or greater is required, " "but only version %d.%d.%d was found. You may be able to obtain a more recent copy " "from http://www.libsdl.org/.", ver.major, ver.minor, ver.patch ), "SDL Library Too Old" ); Sys_Exit( 1 ); } #endif Sys_PlatformInit( ); // Set the initial time base Sys_Milliseconds( ); #ifdef MACOS_X // This is passed if we are launched by double-clicking if ( argc >= 2 && Q_strncmp ( argv[1], "-psn", 4 ) == 0 ) argc = 1; #endif Sys_ParseArgs( argc, argv ); Sys_SetBinaryPath( Sys_Dirname( argv[ 0 ] ) ); Sys_SetDefaultInstallPath( DEFAULT_BASEDIR ); // Concatenate the command line for passing to Com_Init for( i = 1; i < argc; i++ ) { const qboolean containsSpaces = strchr(argv[i], ' ') != NULL; if (containsSpaces) Q_strcat( commandLine, sizeof( commandLine ), "\"" ); Q_strcat( commandLine, sizeof( commandLine ), argv[ i ] ); if (containsSpaces) Q_strcat( commandLine, sizeof( commandLine ), "\"" ); Q_strcat( commandLine, sizeof( commandLine ), " " ); } Com_Init( commandLine ); NET_Init( ); CON_Init( ); signal( SIGILL, Sys_SigHandler ); signal( SIGFPE, Sys_SigHandler ); signal( SIGSEGV, Sys_SigHandler ); signal( SIGTERM, Sys_SigHandler ); signal( SIGINT, Sys_SigHandler ); while( 1 ) { IN_Frame( ); Com_Frame( ); } return 0; }