1
0
Fork 0
forked from fte/fteqw

Add BPTC (aka: bc6+bc7) fallback decompression.

Fix some warnings.
Work around ezquake's PEXT_TRANS bug - now properly gets disabled.


git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@5500 fc73d0e0-1445-4013-8a0c-d673dee63da5
This commit is contained in:
Spoike 2019-08-01 02:13:44 +00:00
parent c159d90253
commit 7991260cc0
21 changed files with 3752 additions and 2711 deletions

View file

@ -119,6 +119,12 @@ ENDIF()
IF(CMAKE_C_COMPILER_ID MATCHES "Clang") IF(CMAKE_C_COMPILER_ID MATCHES "Clang")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-pointer-sign") set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wno-pointer-sign")
IF(CMAKE_BUILD_TYPE MATCHES "Debug")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Werror -Wno-pointer-sign -Wno-unknown-pragmas -Wno-format-zero-length -Wno-strict-aliasing -Wno-error=cpp")
ELSE()
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -O3")
ENDIF()
endif() endif()
IF(CMAKE_C_COMPILER_ID MATCHES "GNU") IF(CMAKE_C_COMPILER_ID MATCHES "GNU")
SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wstrict-prototypes") # SET(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wstrict-prototypes") #
@ -133,7 +139,7 @@ IF(CMAKE_C_COMPILER_ID MATCHES "GNU")
#might as well do this, public builds use the regular Makefile. #might as well do this, public builds use the regular Makefile.
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -march=native") set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -march=native")
IF(CMAKE_BUILD_TYPE MATCHES "Debug") IF(CMAKE_BUILD_TYPE MATCHES "Debug")
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Wcast-align -Werror -Wno-pointer-sign -Wno-unknown-pragmas -Wno-format-zero-length -Wno-strict-aliasing -Wno-error=cpp") set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -Wall -Werror -Wno-pointer-sign -Wno-unknown-pragmas -Wno-format-zero-length -Wno-strict-aliasing -Wno-error=cpp")
ELSE() ELSE()
set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -O3") set(CMAKE_C_FLAGS "${CMAKE_C_FLAGS} -O3")
ENDIF() ENDIF()

View file

@ -390,9 +390,9 @@ int AAS_NearestEntity(vec3_t origin, int modelindex)
ent = &aasworld.entities[i]; ent = &aasworld.entities[i];
if (ent->i.modelindex != modelindex) continue; if (ent->i.modelindex != modelindex) continue;
VectorSubtract(ent->i.origin, origin, dir); VectorSubtract(ent->i.origin, origin, dir);
if (abs(dir[0]) < 40) if (fabs(dir[0]) < 40)
{ {
if (abs(dir[1]) < 40) if (fabs(dir[1]) < 40)
{ {
dist = VectorLength(dir); dist = VectorLength(dir);
if (dist < bestdist) if (dist < bestdist)

View file

@ -168,7 +168,7 @@ int AAS_AgainstLadder(vec3_t origin)
//get the plane the face is in //get the plane the face is in
plane = &aasworld.planes[face->planenum ^ side]; plane = &aasworld.planes[face->planenum ^ side];
//if the origin is pretty close to the plane //if the origin is pretty close to the plane
if (abs(DotProduct(plane->normal, origin) - plane->dist) < 3) if (fabs(DotProduct(plane->normal, origin) - plane->dist) < 3)
{ {
if (AAS_PointInsideFace(abs(facenum), origin, 0.1f)) return qtrue; if (AAS_PointInsideFace(abs(facenum), origin, 0.1f)) return qtrue;
} //end if } //end if

View file

@ -2464,8 +2464,8 @@ int AAS_Reachability_Ladder(int area1num, int area2num)
VectorMA(area1point, -32, dir, area1point); VectorMA(area1point, -32, dir, area1point);
VectorMA(area2point, 32, dir, area2point); VectorMA(area2point, 32, dir, area2point);
// //
ladderface1vertical = abs(DotProduct(plane1->normal, up)) < 0.1; ladderface1vertical = fabs(DotProduct(plane1->normal, up)) < 0.1;
ladderface2vertical = abs(DotProduct(plane2->normal, up)) < 0.1; ladderface2vertical = fabs(DotProduct(plane2->normal, up)) < 0.1;
//there's only reachability between vertical ladder faces //there's only reachability between vertical ladder faces
if (!ladderface1vertical && !ladderface2vertical) return qfalse; if (!ladderface1vertical && !ladderface2vertical) return qfalse;
//if both vertical ladder faces //if both vertical ladder faces
@ -2473,7 +2473,7 @@ int AAS_Reachability_Ladder(int area1num, int area2num)
//and the ladder faces do not make a sharp corner //and the ladder faces do not make a sharp corner
&& DotProduct(plane1->normal, plane2->normal) > 0.7 && DotProduct(plane1->normal, plane2->normal) > 0.7
//and the shared edge is not too vertical //and the shared edge is not too vertical
&& abs(DotProduct(sharededgevec, up)) < 0.7) && fabs(DotProduct(sharededgevec, up)) < 0.7)
{ {
//create a new reachability link //create a new reachability link
lreach = AAS_AllocReachability(); lreach = AAS_AllocReachability();
@ -2598,7 +2598,7 @@ int AAS_Reachability_Ladder(int area1num, int area2num)
if (face2->faceflags & FACE_LADDER) if (face2->faceflags & FACE_LADDER)
{ {
plane2 = &aasworld.planes[face2->planenum]; plane2 = &aasworld.planes[face2->planenum];
if (abs(DotProduct(plane2->normal, up)) < 0.1) break; if (fabs(DotProduct(plane2->normal, up)) < 0.1) break;
} //end if } //end if
} //end for } //end for
//if from another area without vertical ladder faces //if from another area without vertical ladder faces

View file

@ -2056,7 +2056,7 @@ bot_moveresult_t BotTravel_Elevator(bot_movestate_t *ms, aas_reachability_t *rea
botimport.Print(PRT_MESSAGE, "bot on elevator\n"); botimport.Print(PRT_MESSAGE, "bot on elevator\n");
#endif //DEBUG_ELEVATOR #endif //DEBUG_ELEVATOR
//if vertically not too far from the end point //if vertically not too far from the end point
if (abs(ms->origin[2] - reach->end[2]) < sv_maxbarrier->value) if (fabs(ms->origin[2] - reach->end[2]) < sv_maxbarrier->value)
{ {
#ifdef DEBUG_ELEVATOR #ifdef DEBUG_ELEVATOR
botimport.Print(PRT_MESSAGE, "bot moving to end\n"); botimport.Print(PRT_MESSAGE, "bot moving to end\n");

View file

@ -2468,7 +2468,7 @@ int PC_Directive_eval(source_t *source)
token.whitespace_p = source->scriptstack->script_p; token.whitespace_p = source->scriptstack->script_p;
token.endwhitespace_p = source->scriptstack->script_p; token.endwhitespace_p = source->scriptstack->script_p;
token.linescrossed = 0; token.linescrossed = 0;
sprintf(token.string, "%d", abs(value)); sprintf(token.string, "%d", abs((int)value));
token.type = TT_NUMBER; token.type = TT_NUMBER;
token.subtype = TT_INTEGER|TT_LONG|TT_DECIMAL; token.subtype = TT_INTEGER|TT_LONG|TT_DECIMAL;
PC_UnreadSourceToken(source, &token); PC_UnreadSourceToken(source, &token);
@ -2573,12 +2573,12 @@ int PC_DollarDirective_evalint(source_t *source)
token.whitespace_p = source->scriptstack->script_p; token.whitespace_p = source->scriptstack->script_p;
token.endwhitespace_p = source->scriptstack->script_p; token.endwhitespace_p = source->scriptstack->script_p;
token.linescrossed = 0; token.linescrossed = 0;
sprintf(token.string, "%d", abs(value)); sprintf(token.string, "%d", abs((int)value));
token.type = TT_NUMBER; token.type = TT_NUMBER;
token.subtype = TT_INTEGER|TT_LONG|TT_DECIMAL; token.subtype = TT_INTEGER|TT_LONG|TT_DECIMAL;
#ifdef NUMBERVALUE #ifdef NUMBERVALUE
token.intvalue = abs(value); token.intvalue = labs(value);
token.floatvalue = token.intvalue; token.floatvalue = token.intvalue;
#endif //NUMBERVALUE #endif //NUMBERVALUE

View file

@ -3237,7 +3237,7 @@ static void CLQW_ParseServerData (void)
str = MSG_ReadString (); str = MSG_ReadString ();
Con_DPrintf("Server is using gamedir \"%s\"\n", str); Con_DPrintf("Server is using gamedir \"%s\"\n", str);
if (!*str) if (!*str)
str = "qw"; str = "qw"; //FIXME: query active manifest's basegamedir
#ifndef CLIENTONLY #ifndef CLIENTONLY
if (!sv.state) if (!sv.state)

File diff suppressed because it is too large Load diff

View file

@ -109,6 +109,7 @@
#undef DECOMPRESS_ETC2 #undef DECOMPRESS_ETC2
#undef DECOMPRESS_RGTC #undef DECOMPRESS_RGTC
#undef DECOMPRESS_S3TC #undef DECOMPRESS_S3TC
#undef DECOMPRESS_BPTC //bc6+bc7
#undef NETPREPARSE //allows for running both nq+qw on the same server (if not, protocol used must match gamecode). #undef NETPREPARSE //allows for running both nq+qw on the same server (if not, protocol used must match gamecode).
#undef USE_SQLITE //sql-database-as-file support #undef USE_SQLITE //sql-database-as-file support
#undef QUAKESTATS //defines STAT_HEALTH etc. if omitted, you'll need to provide that functionality yourself. #undef QUAKESTATS //defines STAT_HEALTH etc. if omitted, you'll need to provide that functionality yourself.

View file

@ -103,6 +103,7 @@
#define DECOMPRESS_ETC2 //decompress etc2(core in gles3/gl4.3) if the graphics driver doesn't support it (eg d3d or crappy gpus with vulkan). #define DECOMPRESS_ETC2 //decompress etc2(core in gles3/gl4.3) if the graphics driver doesn't support it (eg d3d or crappy gpus with vulkan).
#define DECOMPRESS_S3TC //allows bc1-3 to work even when drivers don't support it. This is probably only an issue on mobile chips. WARNING: not entirely sure if all patents expired yet... #define DECOMPRESS_S3TC //allows bc1-3 to work even when drivers don't support it. This is probably only an issue on mobile chips. WARNING: not entirely sure if all patents expired yet...
#define DECOMPRESS_RGTC //bc4+bc5 #define DECOMPRESS_RGTC //bc4+bc5
#define DECOMPRESS_BPTC //bc6+bc7
// Game/Gamecode Support // Game/Gamecode Support
#define CSQC_DAT #define CSQC_DAT

View file

@ -105,6 +105,7 @@
//#define DECOMPRESS_ETC2 //decompress etc2(core in gles3/gl4.3) if the graphics driver doesn't support it (eg d3d or crappy gpus with vulkan). //#define DECOMPRESS_ETC2 //decompress etc2(core in gles3/gl4.3) if the graphics driver doesn't support it (eg d3d or crappy gpus with vulkan).
//#define DECOMPRESS_S3TC //allows bc1-3 to work even when drivers don't support it. This is probably only an issue on mobile chips. WARNING: not entirely sure if all patents expired yet... //#define DECOMPRESS_S3TC //allows bc1-3 to work even when drivers don't support it. This is probably only an issue on mobile chips. WARNING: not entirely sure if all patents expired yet...
//#define DECOMPRESS_RGTC //bc4+bc5 //#define DECOMPRESS_RGTC //bc4+bc5
//#define DECOMPRESS_BPTC //bc6+bc7
// Game/Gamecode Support // Game/Gamecode Support
//#define CSQC_DAT //#define CSQC_DAT

View file

@ -102,7 +102,8 @@
#define AVAIL_FREETYPE //for truetype font rendering #define AVAIL_FREETYPE //for truetype font rendering
#define DECOMPRESS_ETC2 //decompress etc2(core in gles3/gl4.3) if the graphics driver doesn't support it (eg d3d or crappy gpus with vulkan). #define DECOMPRESS_ETC2 //decompress etc2(core in gles3/gl4.3) if the graphics driver doesn't support it (eg d3d or crappy gpus with vulkan).
//#define DECOMPRESS_S3TC //allows bc1-3 to work even when drivers don't support it. This is probably only an issue on mobile chips. WARNING: not entirely sure if all patents expired yet... //#define DECOMPRESS_S3TC //allows bc1-3 to work even when drivers don't support it. This is probably only an issue on mobile chips. WARNING: not entirely sure if all patents expired yet...
#define DECOMPRESS_RGTC //bc4+bc5 //#define DECOMPRESS_RGTC //bc4+bc5
//#define DECOMPRESS_BPTC //bc6+bc7
// Game/Gamecode Support // Game/Gamecode Support
#define CSQC_DAT #define CSQC_DAT

View file

@ -54,6 +54,7 @@
#define DECOMPRESS_ETC2 #define DECOMPRESS_ETC2
#define DECOMPRESS_RGTC #define DECOMPRESS_RGTC
#define DECOMPRESS_S3TC #define DECOMPRESS_S3TC
#define DECOMPRESS_BPTC //bc6+bc7
#define NOBUILTINMENUS #define NOBUILTINMENUS
#define NOLEGACY #define NOLEGACY
#define AVAIL_DINPUT #define AVAIL_DINPUT

View file

@ -421,7 +421,7 @@ static inline uint32_t get_unaligned_le32(const uint8_t *buf)
} }
#endif #endif
#ifndef get_unaligned_be32 /*#ifndef get_unaligned_be32
static inline uint32_t get_unaligned_be32(const uint8_t *buf) static inline uint32_t get_unaligned_be32(const uint8_t *buf)
{ {
return (uint32_t)(buf[0] << 24) return (uint32_t)(buf[0] << 24)
@ -449,7 +449,7 @@ static inline void put_unaligned_be32(uint32_t val, uint8_t *buf)
buf[2] = (uint8_t)(val >> 8); buf[2] = (uint8_t)(val >> 8);
buf[3] = (uint8_t)val; buf[3] = (uint8_t)val;
} }
#endif #endif*/
/* /*
* Use get_unaligned_le32() also for aligned access for simplicity. On * Use get_unaligned_le32() also for aligned access for simplicity. On

View file

@ -2659,7 +2659,7 @@ static shaderkey_t shaderkeys[] =
// {"albedomap", Shader_DiffuseMap, "fte"}, //rgb(a) // {"albedomap", Shader_DiffuseMap, "fte"}, //rgb(a)
// {"loweruppermap", Shader_LowerUpperMap, "fte"}, //r=lower, g=upper (team being more important than personal colours, this allows the texture to gracefully revert to red-only) // {"loweruppermap", Shader_LowerUpperMap, "fte"}, //r=lower, g=upper (team being more important than personal colours, this allows the texture to gracefully revert to red-only)
//{"normalmap", Shader_NormalMap, "fte"}, //xy-h //{"normalmap", Shader_NormalMap, "fte"}, //xy-h
// {"omrmap", Shader_SpecularMap, "fte"}, //r=occlusion, g=metalness, b=roughness. // {"ormmap", Shader_SpecularMap, "fte"}, //r=occlusion, g=metalness, b=roughness.
//{"glowmap", Shader_FullbrightMap, "fte"}, //rgb //{"glowmap", Shader_FullbrightMap, "fte"}, //rgb
/*program stuff at the material level is an outdated practise.*/ /*program stuff at the material level is an outdated practise.*/

View file

@ -3181,7 +3181,6 @@ QCC_sref_t QCC_PR_StatementFlags ( QCC_opcode_t *op, QCC_sref_t var_a, QCC_sref_
case OP_SUB_PF: case OP_SUB_PF:
case OP_SUB_PI: case OP_SUB_PI:
var_c = var_a; var_c = var_a;
var_b = var_b;
if (op == &pr_opcodes[OP_SUB_PF]) if (op == &pr_opcodes[OP_SUB_PF])
var_b = QCC_SupplyConversion(var_b, ev_integer, true); //FIXME: this should be an unconditional float->int conversion var_b = QCC_SupplyConversion(var_b, ev_integer, true); //FIXME: this should be an unconditional float->int conversion
if (var_c.cast->aux_type->type == ev_void) //void* is treated as a byte type. if (var_c.cast->aux_type->type == ev_void) //void* is treated as a byte type.
@ -9999,6 +9998,8 @@ QCC_ref_t *QCC_PR_RefExpression (QCC_ref_t *retbuf, int priority, int exprflags)
QCC_PR_Statement(&pr_opcodes[OP_GOTO], nullsref, nullsref, &elsej); QCC_PR_Statement(&pr_opcodes[OP_GOTO], nullsref, nullsref, &elsej);
fromj->b.ofs = &statements[numstatements] - fromj; fromj->b.ofs = &statements[numstatements] - fromj;
} }
else
elsej = NULL;
val = QCC_PR_Expression(TOP_PRIORITY, EXPR_DISALLOW_COMMA); val = QCC_PR_Expression(TOP_PRIORITY, EXPR_DISALLOW_COMMA);
if (val.cast->type == ev_integer && !QCC_OPCodeValid(&pr_opcodes[OP_STORE_I])) if (val.cast->type == ev_integer && !QCC_OPCodeValid(&pr_opcodes[OP_STORE_I]))
val = QCC_SupplyConversion(val, ev_float, true); val = QCC_SupplyConversion(val, ev_float, true);
@ -10034,7 +10035,8 @@ QCC_ref_t *QCC_PR_RefExpression (QCC_ref_t *retbuf, int priority, int exprflags)
} }
QCC_FreeTemp(QCC_PR_StatementFlags(&pr_opcodes[(r.cast->size>=3)?OP_STORE_V:OP_STORE_F], val, r, NULL, STFL_PRESERVEB)); QCC_FreeTemp(QCC_PR_StatementFlags(&pr_opcodes[(r.cast->size>=3)?OP_STORE_V:OP_STORE_F], val, r, NULL, STFL_PRESERVEB));
elsej->a.ofs = &statements[numstatements] - elsej; if (elsej)
elsej->a.ofs = &statements[numstatements] - elsej;
return QCC_DefToRef(retbuf, r); return QCC_DefToRef(retbuf, r);
} }
@ -14974,9 +14976,7 @@ QCC_type_t *QCC_PR_ParseEnum(pbool flags)
strictenum = QCC_PR_CheckName("class"); //c++11 style strictenum = QCC_PR_CheckName("class"); //c++11 style
type = QCC_PR_ParseType(false, true); //legacy behaviour type = QCC_PR_ParseType(false, true); //legacy behaviour
if (type) if (!type)
basetype = basetype;
else
{ {
basetype = (flag_assume_integer?type_integer:type_float); basetype = (flag_assume_integer?type_integer:type_float);
if (pr_token_type == tt_name) if (pr_token_type == tt_name)

View file

@ -143,8 +143,6 @@ cvar_t sv_master = CVAR("sv_master", "0");
cvar_t sv_masterport = CVAR("sv_masterport", "0"); cvar_t sv_masterport = CVAR("sv_masterport", "0");
#endif #endif
cvar_t pext_ezquake_nochunks = CVARD("pext_ezquake_nochunks", "0", "Prevents ezquake clients from being able to use the chunked download extension. This sidesteps numerous ezquake issues, and will make downloads slower but more robust.");
cvar_t sv_reliable_sound = CVARFD("sv_reliable_sound", "0", 0, "Causes all sounds to be sent reliably, so they will not be missed due to packetloss. However, this will cause them to be delayed somewhat, and slightly bursty. This can be overriden using the 'rsnd' userinfo setting (either forced on or forced off). Note: this does not affect sounds attached to particle effects."); cvar_t sv_reliable_sound = CVARFD("sv_reliable_sound", "0", 0, "Causes all sounds to be sent reliably, so they will not be missed due to packetloss. However, this will cause them to be delayed somewhat, and slightly bursty. This can be overriden using the 'rsnd' userinfo setting (either forced on or forced off). Note: this does not affect sounds attached to particle effects.");
cvar_t sv_gamespeed = CVARAF("sv_gamespeed", "1", "slowmo", 0); cvar_t sv_gamespeed = CVARAF("sv_gamespeed", "1", "slowmo", 0);
cvar_t sv_csqcdebug = CVARD("sv_csqcdebug", "0", "Inject packet size information for data directed to csqc."); cvar_t sv_csqcdebug = CVARD("sv_csqcdebug", "0", "Inject packet size information for data directed to csqc.");
@ -2779,34 +2777,6 @@ void SV_DoDirectConnect(svconnectinfo_t *fte_restrict info)
} }
newcl->zquake_extensions &= SERVER_SUPPORTED_Z_EXTENSIONS; newcl->zquake_extensions &= SERVER_SUPPORTED_Z_EXTENSIONS;
//ezquake's download mechanism is so smegging buggy.
//its causing far far far too many connectivity issues. seriously. its beyond a joke. I cannot stress that enough.
//as the client needs to listen for the serverinfo to know which extensions will actually be used (yay demos), we can just forget that it supports svc-level extensions, at least for anything that isn't spammed via clc_move etc before the serverinfo.
s = InfoBuf_ValueForKey(&newcl->userinfo, "*client");
if (!strncmp(s, "ezQuake", 7))
{
if (newcl->fteprotocolextensions & PEXT_CHUNKEDDOWNLOADS)
{
if (pext_ezquake_nochunks.ival)
{
newcl->fteprotocolextensions &= ~PEXT_CHUNKEDDOWNLOADS;
Con_TPrintf("%s: ignoring ezquake chunked downloads extension.\n", NET_AdrToString (adrbuf, sizeof(adrbuf), &info->adr));
}
}
if (newcl->zquake_extensions & (Z_EXT_PF_SOLID|Z_EXT_PF_ONGROUND))
{
if (newcl->fteprotocolextensions & PEXT_HULLSIZE)
Con_TPrintf("%s: ezquake - ignoring hullsize extension (conflicts with z_ext_pf_onground).\n", NET_AdrToString (adrbuf, sizeof(adrbuf), &info->adr));
if (newcl->fteprotocolextensions & PEXT_SCALE)
Con_TPrintf("%s: ezquake - ignoring scale extension (conflicts with z_ext_pf_solid).\n", NET_AdrToString (adrbuf, sizeof(adrbuf), &info->adr));
if (newcl->fteprotocolextensions & PEXT_FATNESS)
Con_TPrintf("%s: ezquake - ignoring fatness extension (conflicts with z_ext_pf_solid).\n", NET_AdrToString (adrbuf, sizeof(adrbuf), &info->adr));
if (newcl->fteprotocolextensions & PEXT_TRANS)
Con_TPrintf("%s: ezquake - ignoring transparency extension (buggy on players, conflicts with z_ext_pf_solid).\n", NET_AdrToString (adrbuf, sizeof(adrbuf), &info->adr));
newcl->fteprotocolextensions &= ~(PEXT_HULLSIZE|PEXT_TRANS|PEXT_SCALE|PEXT_FATNESS);
}
}
Netchan_Setup (NS_SERVER, &newcl->netchan, &info->adr, info->qport); Netchan_Setup (NS_SERVER, &newcl->netchan, &info->adr, info->qport);
#ifdef HUFFNETWORK #ifdef HUFFNETWORK
@ -3417,7 +3387,7 @@ void SVC_DirectConnect(int expectedreliablesequence)
} }
msg_badread=false; msg_badread=false;
if (!info.guid) if (!*info.guid)
NET_GetConnectionCertificate(svs.sockets, &net_from, QCERT_PEERFINGERPRINT, info.guid, sizeof(info.guid)); NET_GetConnectionCertificate(svs.sockets, &net_from, QCERT_PEERFINGERPRINT, info.guid, sizeof(info.guid));
info.adr = net_from; info.adr = net_from;
@ -5415,7 +5385,6 @@ void SV_InitLocal (void)
Cvar_Register (&sv_nailhack, cvargroup_servercontrol); Cvar_Register (&sv_nailhack, cvargroup_servercontrol);
Cvar_Register (&sv_nopvs, cvargroup_servercontrol); Cvar_Register (&sv_nopvs, cvargroup_servercontrol);
Cvar_Register (&pext_ezquake_nochunks, cvargroup_servercontrol);
Cmd_AddCommand ("sv_impulse", SV_Impulse_f); Cmd_AddCommand ("sv_impulse", SV_Impulse_f);

View file

@ -73,13 +73,15 @@ cvar_t sv_maxpitch = CVARAFD("maxpitch", "", "sv_maxpitch", CVAR_SERVERINFO, "
cvar_t sv_cmdlikercon = CVAR("sv_cmdlikercon", "0"); //set to 1 to allow a password of username:password instead of the correct rcon password. cvar_t sv_cmdlikercon = CVAR("sv_cmdlikercon", "0"); //set to 1 to allow a password of username:password instead of the correct rcon password.
cvar_t cmd_allowaccess = CVAR("cmd_allowaccess", "0"); //set to 1 to allow cmd to execute console commands on the server. cvar_t cmd_allowaccess = CVAR("cmd_allowaccess", "0"); //set to 1 to allow cmd to execute console commands on the server.
cvar_t cmd_gamecodelevel = CVAR("cmd_gamecodelevel", STRINGIFY(RESTRICT_LOCAL)); //execution level which gamecode is told about (for unrecognised commands) cvar_t cmd_gamecodelevel = CVARF("cmd_gamecodelevel", STRINGIFY(RESTRICT_LOCAL), CVAR_NOTFROMSERVER); //execution level which gamecode is told about (for unrecognised commands)
cvar_t sv_pure = CVARFD("sv_pure", "", CVAR_SERVERINFO, "The most evil cvar in the world, many clients will ignore this.\n0=standard quake rules.\n1=clients should prefer files within packages present on the server.\n2=clients should use *only* files within packages present on the server.\nDue to quake 1.01/1.06 differences, a setting of 2 only works in total conversions."); cvar_t sv_pure = CVARFD("sv_pure", "", CVAR_SERVERINFO, "The most evil cvar in the world, many clients will ignore this.\n0=standard quake rules.\n1=clients should prefer files within packages present on the server.\n2=clients should use *only* files within packages present on the server.\nDue to quake 1.01/1.06 differences, a setting of 2 only works in total conversions.");
cvar_t sv_nqplayerphysics = CVARAFCD("sv_nqplayerphysics", "auto", "sv_nomsec", 0, SV_NQPhysicsUpdate, "Disable player prediction and run NQ-style player physics instead. This can be used for compatibility with mods that expect exact behaviour."); cvar_t sv_nqplayerphysics = CVARAFCD("sv_nqplayerphysics", "auto", "sv_nomsec", 0, SV_NQPhysicsUpdate, "Disable player prediction and run NQ-style player physics instead. This can be used for compatibility with mods that expect exact behaviour.");
#ifdef HAVE_LEGACY #ifdef HAVE_LEGACY
cvar_t sv_brokenmovetypes = CVARD("sv_brokenmovetypes", "0", "Emulate vanilla quakeworld by forcing MOVETYPE_WALK on all players. Shouldn't be used for any games other than QuakeWorld."); static cvar_t sv_brokenmovetypes = CVARD("sv_brokenmovetypes", "0", "Emulate vanilla quakeworld by forcing MOVETYPE_WALK on all players. Shouldn't be used for any games other than QuakeWorld.");
static cvar_t pext_ezquake_nochunks = CVARD("pext_ezquake_nochunks", "0", "Prevents ezquake clients from being able to use the chunked download extension. This sidesteps numerous ezquake issues, and will make downloads slower but more robust.");
static cvar_t pext_ezquake_verfortrans = CVARD("pext_ezquake_verfortrans", "999999999", "ezQuake does not implement PEXT_TRANS properly. This is the version of ezquake required for PEXT_TRANS to be allowed. This was still broken when I wrote this description, hence the large value.");
#endif #endif
cvar_t sv_chatfilter = CVAR("sv_chatfilter", "0"); cvar_t sv_chatfilter = CVAR("sv_chatfilter", "0");
@ -302,6 +304,42 @@ void SV_New_f (void)
return; return;
} }
#ifdef HAVE_LEGACY
{
//be prepared to recognise client versions, in order to block known-buggy extensions.
const char *s;
int ver;
s = InfoBuf_ValueForKey(&host_client->userinfo, "*client");
if (!strncmp(s, "ezQuake", 7))
{
s += 7;
COM_Parse(s);
ver = atoi(com_token);
//this should actually have been resolved now, but for future use...
if ((host_client->fteprotocolextensions & PEXT_CHUNKEDDOWNLOADS) && pext_ezquake_nochunks.ival)
{
host_client->fteprotocolextensions &= ~PEXT_CHUNKEDDOWNLOADS;
SV_PrintToClient(host_client, PRINT_HIGH, "ezQuake's implementation of chunked downloads is blocked on this server.\n");
}
if ((host_client->zquake_extensions & (Z_EXT_PF_SOLID|Z_EXT_PF_ONGROUND)) && ver < pext_ezquake_verfortrans.ival)
{
if (host_client->fteprotocolextensions & PEXT_HULLSIZE)
SV_PrintToClient(host_client, PRINT_HIGH, "ezQuake's implementation of PEXT_HULLSIZE conflicts with zquake extensions.\n");
if (host_client->fteprotocolextensions & PEXT_SCALE)
SV_PrintToClient(host_client, PRINT_HIGH, "ezQuake's implementation of PEXT_SCALE conflicts with zquake extensions.\n");
if (host_client->fteprotocolextensions & PEXT_FATNESS)
SV_PrintToClient(host_client, PRINT_HIGH, "ezQuake's implementation of PEXT_FATNESS conflicts with zquake extensions.\n");
if (host_client->fteprotocolextensions & PEXT_TRANS)
SV_PrintToClient(host_client, PRINT_HIGH, "ezQuake's implementation of PEXT_TRANS is buggy. Disabling.\n");
host_client->fteprotocolextensions &= ~(PEXT_HULLSIZE|PEXT_TRANS|PEXT_SCALE|PEXT_FATNESS);
}
}
//its not that I'm singling out ezquake or anything, but it has too many people using outdated versions that its hard to ignore.
}
#endif
ClientReliableCheckBlock(host_client, 800); //okay, so it might be longer, but I'm too lazy to work out the real size. ClientReliableCheckBlock(host_client, 800); //okay, so it might be longer, but I'm too lazy to work out the real size.
// send the serverdata // send the serverdata
@ -8687,6 +8725,8 @@ void SV_UserInit (void)
#ifdef HAVE_LEGACY #ifdef HAVE_LEGACY
Cvar_Register (&sv_brokenmovetypes, "Backwards compatability"); Cvar_Register (&sv_brokenmovetypes, "Backwards compatability");
Cvar_Register (&pext_ezquake_nochunks, cvargroup_servercontrol);
Cvar_Register (&pext_ezquake_verfortrans, cvargroup_servercontrol);
#endif #endif
} }

View file

@ -255,6 +255,23 @@ static void ParseServerData(sv_t *tv, netmsg_t *m, int to, unsigned int playerma
tv->map.trackplayer = -1; tv->map.trackplayer = -1;
ReadString(m, tv->map.gamedir, sizeof(tv->map.gamedir)); ReadString(m, tv->map.gamedir, sizeof(tv->map.gamedir));
#define DEFAULTGAMEDIR "qw"
if (strchr(tv->map.gamedir, ':')) //nuke any multiple gamedirs - we need to read maps which would fail if its not a valid single path.
*strchr(tv->map.gamedir, ';') = 0;
if (!*tv->map.gamedir)
strcpy(tv->map.gamedir, DEFAULTGAMEDIR);
if (!*tv->map.gamedir
|| *tv->map.gamedir == '.'
|| !strcmp(tv->map.gamedir, ".")
|| strstr(tv->map.gamedir, "..")
|| strstr(tv->map.gamedir, "/")
|| strstr(tv->map.gamedir, "\\")
|| strstr(tv->map.gamedir, ":")
)
{
QTV_Printf(tv, "Ignoring unsafe gamedir: \"%s\"\n", tv->map.gamedir);
strcpy(tv->map.gamedir, DEFAULTGAMEDIR);
}
if (tv->usequakeworldprotocols) if (tv->usequakeworldprotocols)
tv->map.thisplayer = ReadByte(m)&~128; tv->map.thisplayer = ReadByte(m)&~128;
@ -492,7 +509,7 @@ static void ParseStufftext(sv_t *tv, netmsg_t *m, int to, unsigned int mask)
{ {
Multicast(tv, (char*)m->data+m->startpos, m->readpos - m->startpos, to, mask, Q1); Multicast(tv, (char*)m->data+m->startpos, m->readpos - m->startpos, to, mask, Q1);
if (!tv->controller) if (!tv->controller)
SendClientCommand(tv, text); SendClientCommand(tv, "%s", text);
} }
else else
{ {
@ -895,7 +912,7 @@ static void ParseEntityDelta(sv_t *tv, netmsg_t *m, const entity_state_t *old, e
if (flags & UX_ALPHA) if (flags & UX_ALPHA)
new->alpha = ReadByte(m); new->alpha = ReadByte(m);
if (flags & UX_FATNESS) if (flags & UX_FATNESS)
/*new->fatness =*/ (signed char)ReadByte(m); /*new->fatness = (signed char)*/ReadByte(m);
if (flags & UX_DRAWFLAGS) if (flags & UX_DRAWFLAGS)
/*new->hexen2flags =*/ ReadByte(m); /*new->hexen2flags =*/ ReadByte(m);
if (flags & UX_ABSLIGHT) if (flags & UX_ABSLIGHT)

View file

@ -1112,7 +1112,7 @@ static int sasl_digestmd5_challenge(struct sasl_ctx_s *ctx, char *in, int inlen,
Q_snprintf(X, sizeof(X), "%s:%s:", username, realm); Q_snprintf(X, sizeof(X), "%s:%s:", username, realm);
if (ctx->password_hash_size == 16 && !strcmp(X, ctx->password_validity)) if (ctx->password_hash_size == 16 && !strcmp(X, ctx->password_validity))
memcpy(Y, ctx->password_hash, 16); //use the hashed password, instead of the (missing) plain one memcpy(Y, ctx->password_hash, 16); //use the hashed password, instead of the (missing) plain one
else if (ctx->password_plain) else if (*ctx->password_plain)
{ {
Q_strlcpy(ctx->password_validity, X, sizeof(ctx->password_validity)); Q_strlcpy(ctx->password_validity, X, sizeof(ctx->password_validity));
@ -2769,7 +2769,7 @@ jclient_t *JCL_ConnectXML(xmltree_t *acc)
jcl->sasl.allowauth_plaintls = atoi(XML_GetChildBody(acc, "allowauth_plain_tls", "1")); //required 1 for googletalk, otherwise I'd set it to 0. jcl->sasl.allowauth_plaintls = atoi(XML_GetChildBody(acc, "allowauth_plain_tls", "1")); //required 1 for googletalk, otherwise I'd set it to 0.
jcl->sasl.allowauth_digestmd5 = atoi(XML_GetChildBody(acc, "allowauth_digest_md5", "1")); jcl->sasl.allowauth_digestmd5 = atoi(XML_GetChildBody(acc, "allowauth_digest_md5", "1"));
jcl->sasl.allowauth_scramsha1 = atoi(XML_GetChildBody(acc, "allowauth_scram_sha_1", "1")); jcl->sasl.allowauth_scramsha1 = atoi(XML_GetChildBody(acc, "allowauth_scram_sha_1", "1"));
jcl->sasl.allowauth_oauth2 = atoi(XML_GetChildBody(acc, "allowauth_oauth2", jcl->sasl.oauth2.saslmethod?"1":"0")); jcl->sasl.allowauth_oauth2 = atoi(XML_GetChildBody(acc, "allowauth_oauth2", *jcl->sasl.oauth2.saslmethod?"1":"0"));
jcl->savepassword = atoi(XML_GetChildBody(acc, "savepassword", "0")); jcl->savepassword = atoi(XML_GetChildBody(acc, "savepassword", "0"));

View file

@ -628,7 +628,7 @@ static void JCL_JingleParsePeerPorts(jclient_t *jcl, struct c2c_s *c2c, xmltree_
int i, contid; int i, contid;
const char *cname; const char *cname;
if (!c2c->sid) if (!*c2c->sid)
return; return;
if (strcmp(c2c->with, from) || strcmp(c2c->sid, sid)) if (strcmp(c2c->with, from) || strcmp(c2c->sid, sid))