be more verbose about the port that we're redirected to when acting as an nq client.

add r_coronas_occlusion cvar. when set to 1, coronas are occluded by mdl geometry rather than just physical stuff. fix hitmodel stuff slightly.
rewrote if command handling. now properly supports operator precedence.
x11: try to fix XIM on ubuntu.
qcc: Add -frootconstructor


git-svn-id: https://svn.code.sf.net/p/fteqw/code/trunk@4986 fc73d0e0-1445-4013-8a0c-d673dee63da5
This commit is contained in:
Spoike 2015-09-10 10:16:26 +00:00
parent f2a9e850a0
commit a38a933fdd
17 changed files with 454 additions and 187 deletions

View File

@ -3139,7 +3139,11 @@ void CLNQ_ConnectionlessPacket(void)
//this is the port that we're meant to respond to. //this is the port that we're meant to respond to.
if (port) if (port)
{
char buf[256];
net_from.port = port; net_from.port = port;
Con_DPrintf("redirecting to port %s\n", NET_AdrToString(buf, sizeof(buf), &net_from));
}
cls.protocol_nq = CPNQ_ID; cls.protocol_nq = CPNQ_ID;
if (MSG_ReadByte() == 1) //a proquake server adds a little extra info if (MSG_ReadByte() == 1) //a proquake server adds a little extra info

View File

@ -1036,6 +1036,7 @@ extern unsigned int cl_maxstris;
extern char emodel_name[], pmodel_name[], prespawn_name[], modellist_name[], soundlist_name[]; extern char emodel_name[], pmodel_name[], prespawn_name[], modellist_name[], soundlist_name[];
unsigned int TraceLineN (vec3_t start, vec3_t end, vec3_t impact, vec3_t normal); unsigned int TraceLineN (vec3_t start, vec3_t end, vec3_t impact, vec3_t normal);
entity_t *TraceLineR (vec3_t start, vec3_t end, vec3_t impact, vec3_t normal);
// //
// cl_input // cl_input

View File

@ -755,6 +755,104 @@ void P_Shutdown(void)
R_Clutter_Purge(); R_Clutter_Purge();
} }
//0 says hit nothing.
//1 says hit world
//>1 says hit some entity
entity_t *TraceLineR (vec3_t start, vec3_t end, vec3_t impact, vec3_t normal)
{
trace_t trace;
float len, bestlen;
int i, j;
vec3_t delta, ts, te;
entity_t *pe;
entity_t *result=NULL;
vec3_t axis[3];
vec3_t movemins, movemaxs;
memset (&trace, 0, sizeof(trace));
VectorSubtract(end, start, delta);
bestlen = Length(delta);
VectorCopy (end, impact);
for (i = 0; i < 3; i++)
{
if (start[i] > end[i])
{
movemins[i] = end[i];
movemaxs[i] = start[i];
}
else
{
movemins[i] = start[i];
movemaxs[i] = end[i];
}
}
for (i=-1 ; i<cl_numvisedicts ; i++)
{
if (i == -1)
pe = &r_worldentity;
else
pe = &cl_visedicts[i];
if (pe->rtype != RT_MODEL || pe->shaderRGBAf[3] < 1 || (pe->flags & (RF_ADDITIVE|RF_NODEPTHTEST|RF_TRANSLUCENT|RF_EXTERNALMODEL)))
continue;
if (pe->model && pe->model->funcs.NativeTrace && pe->model->loadstate == MLS_LOADED)
{
//try to trivially reject the mesh.
float ext = 0;
float t;
for (j = 0; j < 3; j++)
{
t = fabs(pe->model->maxs[j]);
ext = max(ext, t);
t = fabs(pe->model->mins[j]);
ext = max(ext, t);
}
if ( movemins[0] > pe->origin[0]+ext
|| movemins[1] > pe->origin[1]+ext
|| movemins[2] > pe->origin[2]+ext
|| movemaxs[0] < pe->origin[0]-ext
|| movemaxs[1] < pe->origin[1]-ext
|| movemaxs[2] < pe->origin[2]-ext )
continue;
VectorSubtract(start, pe->origin, ts);
VectorSubtract(end, pe->origin, te);
pe->model->funcs.NativeTrace(pe->model, 0, pe->framestate.g[FS_REG].frame[pe->framestate.g[FS_REG].lerpweight[1] > pe->framestate.g[FS_REG].lerpweight[0]], pe->axis, ts, te, vec3_origin, vec3_origin, false, MASK_WORLDSOLID, &trace);
if (trace.fraction<1)
{
VectorSubtract(trace.endpos, ts, delta);
len = Length(delta);
if (len < bestlen)
{
bestlen = len;
if (normal)
VectorCopy (trace.plane.normal, normal);
VectorAdd (pe->origin, trace.endpos, impact);
}
result = pe;
}
/*if (trace.startsolid)
{
VectorNormalize(delta);
if (normal)
{
normal[0] = -delta[0];
normal[1] = -delta[1];
normal[2] = -delta[2];
}
VectorCopy (end, impact);
return NULL;
}*/
}
}
return result;
}
//0 says hit nothing. //0 says hit nothing.
//1 says hit world //1 says hit world
//>1 says hit some entity //>1 says hit some entity

View File

@ -584,7 +584,7 @@ extern cvar_t gl_poly;
extern cvar_t gl_affinemodels; extern cvar_t gl_affinemodels;
extern cvar_t r_renderscale; extern cvar_t r_renderscale;
extern cvar_t gl_nohwblend; extern cvar_t gl_nohwblend;
extern cvar_t r_coronas, r_flashblend, r_flashblendscale; extern cvar_t r_coronas, r_coronas_occlusion, r_flashblend, r_flashblendscale;
extern cvar_t r_lightstylesmooth; extern cvar_t r_lightstylesmooth;
extern cvar_t r_lightstylesmooth_limit; extern cvar_t r_lightstylesmooth_limit;
extern cvar_t r_lightstylespeed; extern cvar_t r_lightstylespeed;

View File

@ -111,8 +111,8 @@ cvar_t r_skin_overlays = SCVARF ("r_skin_overlays", "1",
CVAR_SEMICHEAT|CVAR_RENDERERLATCH); CVAR_SEMICHEAT|CVAR_RENDERERLATCH);
cvar_t r_globalskin_first = CVARFD ("r_globalskin_first", "100", CVAR_RENDERERLATCH, "Specifies the first .skin value that is a global skin. Entities within this range will use the shader/image called 'gfx/skinSKIN.lmp' instead of their regular skin. See also: r_globalskin_count."); cvar_t r_globalskin_first = CVARFD ("r_globalskin_first", "100", CVAR_RENDERERLATCH, "Specifies the first .skin value that is a global skin. Entities within this range will use the shader/image called 'gfx/skinSKIN.lmp' instead of their regular skin. See also: r_globalskin_count.");
cvar_t r_globalskin_count = CVARFD ("r_globalskin_count", "10", CVAR_RENDERERLATCH, "Specifies how many globalskins there are."); cvar_t r_globalskin_count = CVARFD ("r_globalskin_count", "10", CVAR_RENDERERLATCH, "Specifies how many globalskins there are.");
cvar_t r_coronas = SCVARF ("r_coronas", "0", cvar_t r_coronas = CVARFD ("r_coronas", "0", CVAR_ARCHIVE, "Draw coronas on realtime lights. Overrides glquake-esque flashblends.");
CVAR_ARCHIVE); cvar_t r_coronas_occlusion = CVARFD ("r_coronas_occlusion", "1", CVAR_ARCHIVE, "Specifies that coronas should be occluded more carefully.\n0: BSP occlusion only.\n1: non-bsp occlusion also");
cvar_t r_flashblend = SCVARF ("gl_flashblend", "0", cvar_t r_flashblend = SCVARF ("gl_flashblend", "0",
CVAR_ARCHIVE); CVAR_ARCHIVE);
cvar_t r_flashblendscale = SCVARF ("gl_flashblendscale", "0.35", cvar_t r_flashblendscale = SCVARF ("gl_flashblendscale", "0.35",
@ -714,6 +714,7 @@ void Renderer_Init(void)
Cvar_Register(&r_stainfadeammount, GRAPHICALNICETIES); Cvar_Register(&r_stainfadeammount, GRAPHICALNICETIES);
Cvar_Register(&r_lightprepass, GLRENDEREROPTIONS); Cvar_Register(&r_lightprepass, GLRENDEREROPTIONS);
Cvar_Register (&r_coronas, GRAPHICALNICETIES); Cvar_Register (&r_coronas, GRAPHICALNICETIES);
Cvar_Register (&r_coronas_occlusion, GRAPHICALNICETIES);
Cvar_Register (&r_flashblend, GRAPHICALNICETIES); Cvar_Register (&r_flashblend, GRAPHICALNICETIES);
Cvar_Register (&r_flashblendscale, GRAPHICALNICETIES); Cvar_Register (&r_flashblendscale, GRAPHICALNICETIES);
Cvar_Register (&gl_specular, GRAPHICALNICETIES); Cvar_Register (&gl_specular, GRAPHICALNICETIES);

View File

@ -361,6 +361,7 @@ static qboolean OSS_InitCard(soundcardinfo_t *sc, const char *snddev)
} }
#define SDRVNAME "OSS" #define SDRVNAME "OSS"
#if defined(__linux__) && !defined(SNDCTL_SYSINFO)
typedef struct oss_sysinfo { typedef struct oss_sysinfo {
char product[32]; /* E.g. SunOS Audio */ char product[32]; /* E.g. SunOS Audio */
char version[32]; /* E.g. 4.0a */ char version[32]; /* E.g. 4.0a */
@ -380,7 +381,9 @@ typedef struct oss_sysinfo {
int filler[172]; /* Reserved */ int filler[172]; /* Reserved */
} oss_sysinfo; } oss_sysinfo;
#define SNDCTL_SYSINFO _IOR ('X', 1, oss_sysinfo) #define SNDCTL_SYSINFO _IOR ('X', 1, oss_sysinfo)
#endif
#if defined(__linux__) && !defined(SNDCTL_AUDIOINFO)
typedef struct oss_audioinfo { typedef struct oss_audioinfo {
int dev; /* Device to query */ int dev; /* Device to query */
char name[64]; /* Human readable name */ char name[64]; /* Human readable name */
@ -415,9 +418,11 @@ typedef struct oss_audioinfo {
int filler[184]; /* reserved */ int filler[184]; /* reserved */
} oss_audioinfo; } oss_audioinfo;
#define SNDCTL_AUDIOINFO _IOWR('X', 7, oss_audioinfo) #define SNDCTL_AUDIOINFO _IOWR('X', 7, oss_audioinfo)
#endif
static qboolean QDECL OSS_Enumerate(void (QDECL *cb) (const char *drivername, const char *devicecode, const char *readablename)) static qboolean QDECL OSS_Enumerate(void (QDECL *cb) (const char *drivername, const char *devicecode, const char *readablename))
{ {
#if defined(SNDCTL_SYSINFO) && defined(SNDCTL_AUDIOINFO)
int i; int i;
int fd = open("/dev/mixer", O_RDWR, 0); int fd = open("/dev/mixer", O_RDWR, 0);
oss_sysinfo si; oss_sysinfo si;
@ -444,6 +449,7 @@ static qboolean QDECL OSS_Enumerate(void (QDECL *cb) (const char *drivername, co
else else
printf("OSS driver is too old to support device enumeration.\n"); printf("OSS driver is too old to support device enumeration.\n");
close(fd); close(fd);
#endif
return false; //enumeration failed. return false; //enumeration failed.
} }

View File

@ -521,7 +521,7 @@ void Sys_CloseLibrary(dllhandle_t *lib)
dllhandle_t *Sys_LoadLibrary(const char *name, dllfunction_t *funcs) dllhandle_t *Sys_LoadLibrary(const char *name, dllfunction_t *funcs)
{ {
int i; int i;
dllhandle_t lib; dllhandle_t *lib;
lib = NULL; lib = NULL;
if (!lib) if (!lib)

View File

@ -3670,6 +3670,7 @@ static void Sys_MakeInstaller(const char *name)
qbyte *filedata; qbyte *filedata;
unsigned int filelen; unsigned int filelen;
char *error = NULL; char *error = NULL;
char *warn = NULL;
HANDLE bin; HANDLE bin;
char ourname[MAX_OSPATH]; char ourname[MAX_OSPATH];
char newname[MAX_OSPATH]; char newname[MAX_OSPATH];
@ -3687,11 +3688,6 @@ static void Sys_MakeInstaller(const char *name)
error = "BeginUpdateResource failed"; error = "BeginUpdateResource failed";
else else
{ {
//nuke existing icons.
UpdateResource(bin, RT_GROUP_ICON, MAKEINTRESOURCE(1), RESLANG, NULL, 0);
UpdateResource(bin, RT_GROUP_ICON, MAKEINTRESOURCE(2), RESLANG, NULL, 0);
// UpdateResource(bin, RT_GROUP_ICON, MAKEINTRESOURCE(3), RESLANG, NULL, 0);
filehandle = VFSOS_Open(va("%s.png", name), "rb"); filehandle = VFSOS_Open(va("%s.png", name), "rb");
if (filehandle) if (filehandle)
{ {
@ -3707,6 +3703,11 @@ static void Sys_MakeInstaller(const char *name)
VFS_READ(filehandle, filedata, filelen); VFS_READ(filehandle, filedata, filelen);
VFS_CLOSE(filehandle); VFS_CLOSE(filehandle);
//nuke existing icons.
UpdateResource(bin, RT_GROUP_ICON, MAKEINTRESOURCE(1), RESLANG, NULL, 0);
UpdateResource(bin, RT_GROUP_ICON, MAKEINTRESOURCE(2), RESLANG, NULL, 0);
// UpdateResource(bin, RT_GROUP_ICON, MAKEINTRESOURCE(3), RESLANG, NULL, 0);
rgbadata = Read32BitImageFile(filedata, filelen, &imgwidth, &imgheight, &hasalpha, va("%s.png", name)); rgbadata = Read32BitImageFile(filedata, filelen, &imgwidth, &imgheight, &hasalpha, va("%s.png", name));
if (!rgbadata) if (!rgbadata)
error = "unable to read icon image"; error = "unable to read icon image";
@ -3806,7 +3807,7 @@ static void Sys_MakeInstaller(const char *name)
BZ_Free(filedata); BZ_Free(filedata);
} }
else else
error = va("%s.ico not found", name); warn = va("%s.png not found", name);
filehandle = VFSOS_Open(va("%s.fmf", name), "rb"); filehandle = VFSOS_Open(va("%s.fmf", name), "rb");
if (filehandle) if (filehandle)
@ -3830,8 +3831,14 @@ static void Sys_MakeInstaller(const char *name)
MoveFile(tmpname, newname); MoveFile(tmpname, newname);
} }
if (!error)
error = warn;
if (error) if (error)
{
Sys_Printf("%s", error);
Sys_Error("%s", error); Sys_Error("%s", error);
}
} }
#endif #endif

View File

@ -2325,9 +2325,9 @@ typedef struct tempstack_s{
struct tempstack_s *next; struct tempstack_s *next;
char str[1]; char str[1];
} tempstack_t; } tempstack_t;
tempstack_t *ifstack; static tempstack_t *ifstack;
void If_Token_Clear (tempstack_t *mark) static void If_Token_Clear (tempstack_t *mark)
{ {
tempstack_t *ois; tempstack_t *ois;
while(ifstack) while(ifstack)
@ -2340,15 +2340,14 @@ void If_Token_Clear (tempstack_t *mark)
} }
} }
tempstack_t *If_Token_GetMark (void) static tempstack_t *If_Token_GetMark (void)
{ {
return ifstack; return ifstack;
} }
const char *retstring(const char *s) static const char *retstring(const char *s)
{ {
// return s;
tempstack_t *ret; tempstack_t *ret;
ret = (tempstack_t*)Z_Malloc(sizeof(tempstack_t)+strlen(s)); ret = (tempstack_t*)Z_Malloc(sizeof(tempstack_t)+strlen(s));
ret->next = ifstack; ret->next = ifstack;
@ -2356,7 +2355,7 @@ const char *retstring(const char *s)
strcpy(ret->str, s); strcpy(ret->str, s);
return ret->str; return ret->str;
} }
const char *retint(int f) static const char *retint(int f)
{ {
char s[1024]; char s[1024];
tempstack_t *ret; tempstack_t *ret;
@ -2369,26 +2368,32 @@ const char *retint(int f)
strcpy(ret->str, s); strcpy(ret->str, s);
return ret->str; return ret->str;
} }
const char *retfloat(float f) static const char *retbool(qboolean b)
{
if (b)
return "1";
return "";
}
static const char *retfloat(float f)
{ {
char s[1024]; char s[1024];
tempstack_t *ret; tempstack_t *ret;
if (!f) if (!f)
return ""; return "";
sprintf(s, "%f", f); sprintf(s, "%g", f);
ret = (tempstack_t*)Z_Malloc(sizeof(tempstack_t)+strlen(s)); ret = (tempstack_t*)Z_Malloc(sizeof(tempstack_t)+strlen(s));
ret->next = ifstack; ret->next = ifstack;
ifstack=ret; ifstack=ret;
strcpy(ret->str, s); strcpy(ret->str, s);
return ret->str; return ret->str;
} }
qboolean is_numeric (const char *c) static qboolean is_numeric (const char *c)
{ {
return (*c >= '0' && *c <= '9') || return (*c >= '0' && *c <= '9') ||
((*c == '-' || *c == '+') && (c[1] == '.' || (c[1]>='0' && c[1]<='9'))) || ((*c == '-' || *c == '+') && (c[1] == '.' || (c[1]>='0' && c[1]<='9'))) ||
(*c == '.' && (c[1]>='0' && c[1]<='9'))?true:false; (*c == '.' && (c[1]>='0' && c[1]<='9'))?true:false;
} }
qboolean is_true (const char *c) static qboolean is_true (const char *c)
{ {
if (is_numeric(c)) if (is_numeric(c))
return !!atof(c); return !!atof(c);
@ -2398,8 +2403,10 @@ qboolean is_true (const char *c)
return false; return false;
return !!*c; return !!*c;
} }
#define IFPUNCT "(,{})(\':;=!><&|+*/-" #define IF_PRI_MAX 12
const char *If_Token(const char *func, const char **end) #define IFPUNCT "(,{})~\':;=!><&|+*/-"
static const char *If_Token(const char *func, const char **end, int pri);
static const char *If_Token_Term(const char *func, const char **end)
{ {
const char *s, *s2; const char *s, *s2;
cvar_t *var; cvar_t *var;
@ -2445,37 +2452,44 @@ const char *If_Token(const char *func, const char **end)
level++; level++;
s2++; s2++;
} }
func = If_Token(s, end); func = If_Token(s, end, IF_PRI_MAX);
*end = s2+1; *end = s2+1;
s = *end; s = *end;
s2 = func; s2 = func;
// return func;
} }
else if (*com_token == '!') else if (*com_token == '!')
{ {
func = If_Token(s, end); func = If_Token(s, end, 0);
for (s = func; *s; s++); s2 = retbool(!is_true(func));
if (func && *func) }
s2 = ""; else if (*com_token == '~')
else {
s2 = "true"; func = If_Token(s, end, 0);
s2 = retbool(~atoi(func));
} }
else if (!strcmp(com_token, "int")) else if (!strcmp(com_token, "int"))
{ {
func = If_Token(s, end); func = If_Token(s, end, 0);
s2 = retint(atoi(func)); s2 = retint(atoi(func));
} }
else if (!strcmp(com_token, "strlen")) else if (!strcmp(com_token, "strlen"))
{ {
func = If_Token(s, end); func = If_Token(s, end, 0);
s2 = retfloat(strlen(func)); s2 = retfloat(strlen(func));
} }
else if (!strcmp(com_token, "eval"))
{
//read the stuff to the right
func = If_Token(s, end, IFPUNCT);
//and evaluate it
s2 = If_Token(func, &func, IF_PRI_MAX);
}
else if (!strcmp(com_token, "defined")) //functions else if (!strcmp(com_token, "defined")) //functions
{ {
s = COM_ParseToken(s, IFPUNCT); s = COM_ParseToken(s, IFPUNCT);
var = Cvar_FindVar(com_token); var = Cvar_FindVar(com_token);
*end = s; *end = s;
s2 = retstring((var != NULL)?"true":""); s2 = retbool(var != NULL);
} }
else if (!strcmp(com_token, "random")) else if (!strcmp(com_token, "random"))
{ {
@ -2488,9 +2502,9 @@ const char *If_Token(const char *func, const char **end)
if (qrenderer == QR_NONE) if (qrenderer == QR_NONE)
s2 = ""; s2 = "";
else if (!strcmp(com_token, "width")) else if (!strcmp(com_token, "width"))
s2 = retfloat(vid.width); s2 = retint(vid.width);
else if (!strcmp(com_token, "height")) else if (!strcmp(com_token, "height"))
s2 = retfloat(vid.height); s2 = retint(vid.height);
else else
#endif #endif
s2 = ""; s2 = "";
@ -2504,7 +2518,10 @@ const char *If_Token(const char *func, const char **end)
if (var) if (var)
{ {
if ((var->restriction?var->restriction:rcon_level.ival) > Cmd_ExecLevel) if ((var->restriction?var->restriction:rcon_level.ival) > Cmd_ExecLevel)
{
Con_Printf("Console script attempted to read restricted cvar %s\n", var->name);
s2 = "RESTRICTED"; s2 = "RESTRICTED";
}
else else
s2 = var->string; s2 = var->string;
} }
@ -2514,109 +2531,159 @@ const char *If_Token(const char *func, const char **end)
*end = s; *end = s;
s = COM_ParseToken(s, IFPUNCT); return s2;
if (!strcmp(com_token, "=")) //comparisions }
enum
{
IFOP_CAT,
IFOP_MUL,
IFOP_DIV,
IFOP_MOD,
IFOP_ADD,
IFOP_SUB,
IFOP_SHL,
IFOP_SHR,
IFOP_ISIN,
IFOP_ISNOTIN,
IFOP_LT,
IFOP_LE,
IFOP_GT,
IFOP_GE,
IFOP_EQ,
IFOP_NE,
IFOP_BA,
IFOP_XOR,
IFOP_BO,
IFOP_LA,
IFOP_LO
};
static const struct
{
int opnamelen;
const char *opname;
int pri;
int op;
} ifops[] =
{
{3, "cat", 3, IFOP_CAT},
{1, "*", 3, IFOP_MUL},
{3, "mul", 3, IFOP_MUL},
{1, "/", 3, IFOP_DIV},
{3, "div", 3, IFOP_DIV},
{1, "%", 3, IFOP_MOD},
{3, "mod", 3, IFOP_MOD},
{1, "+", 4, IFOP_ADD},
{3, "add", 4, IFOP_ADD},
{1, "-", 4, IFOP_SUB},
{3, "sub", 4, IFOP_SUB},
{2, "<<", 5, IFOP_SHL},
{2, ">>", 5, IFOP_SHR},
{4, "isin",5, IFOP_ISIN}, //fuhquake
{5, "!isin",5, IFOP_ISNOTIN}, //fuhquake
{2, "<=", 6, IFOP_LE},
{1, "<", 6, IFOP_LT},
{2, ">=", 6, IFOP_GE},
{1, ">", 6, IFOP_GT},
{2, "==", 7, IFOP_EQ},
{1, "=", 7, IFOP_EQ},
{5, "equal",7, IFOP_EQ}, //qw262
{2, "!=", 7, IFOP_NE},
{2, "&&", 11, IFOP_LA},
{1, "&", 8, IFOP_BA},
{3, "and", 8, IFOP_BA}, //qw262
{1, "^", 9, IFOP_XOR},
{3, "xor", 8, IFOP_XOR}, //qw262
{2, "||", 12, IFOP_LO},
{1, "|", 10, IFOP_BO},
{2, "or", 10, IFOP_BO} //qw262
};
static const char *If_Operator(int op, const char *left, const char *right)
{
int r;
switch(op)
{ {
func=COM_ParseToken(s, IFPUNCT); case IFOP_CAT:
if (*com_token == '=') //lol. "=" == "==" return retstring(va("%s%s", left, right));
return retfloat(!strcmp(s2, If_Token(func, end))); case IFOP_MUL:
return retfloat(atof(left)*atof(right));
case IFOP_DIV:
return retfloat(atof(left)/atof(right));
case IFOP_MOD:
r = atoi(right);
if (r)
return retfloat(atoi(left)%r);
else else
return retfloat(!strcmp(s2, If_Token(s, end)));
}
if (!strncmp(com_token, "equal", 5))
return retfloat(!strcmp(s2, If_Token(s, end)));
if (!strcmp(com_token, "!"))
{
func=COM_ParseToken(s, IFPUNCT);
if (*com_token == '=')
{
s = If_Token(func, end);
if (!is_numeric(s) || !is_numeric(s2))
{
if (strcmp(s2, s))
return "true";
else
return "";
}
return retfloat(atof(s2)!=atof(s));
}
else if (!strcmp(com_token, "isin"))
return retfloat(NULL==strstr(If_Token(s, end), s2));
}
if (!strcmp(com_token, ">"))
{
func=COM_ParseToken(s, IFPUNCT);
if (*com_token == '=')
return retfloat(atof(s2)>=atof(If_Token(func, end)));
else if (*com_token == '<')//vb?
{
s = If_Token(func, end);
if (is_numeric(s) && is_numeric(s2))
{
if (strcmp(s2, s))
return "true";
else
return "";
}
return retfloat(atof(s2)!=atof(s));
}
else
return retfloat(atof(s2)>atof(If_Token(s, end)));
}
if (!strcmp(com_token, "<"))
{
func=COM_ParseToken(s, IFPUNCT);
if (*com_token == '=')
return retfloat(atof(s2)<=atof(If_Token(func, end)));
else if (*com_token == '>')//vb?
return retfloat(atof(s2)!=atof(If_Token(func, end)));
else
return retfloat(atof(s2)<atof(If_Token(s, end)));
}
if (!strcmp(com_token, "isin"))//fuhq
return retfloat(NULL!=strstr(If_Token(s, end), s2));
if (!strcmp(com_token, "-")) //subtract
return retfloat(atof(s2)-atof(If_Token(s, end)));
if (!strcmp(com_token, "+")) //add
return retfloat(atof(s2)+atof(If_Token(s, end)));
if (!strcmp(com_token, "*"))
return retfloat(atof(s2)*atof(If_Token(s, end)));
if (!strcmp(com_token, "/"))
return retfloat(atof(s2)/atof(If_Token(s, end)));
if (!strcmp(com_token, "%"))
{
level = (int)atof(If_Token(s, end));
if (level == 0)
return retfloat(0); return retfloat(0);
case IFOP_ADD:
return retfloat(atof(left)+atof(right));
case IFOP_SUB:
return retfloat(atof(left)-atof(right));
case IFOP_SHL:
return retfloat(atoi(left)<<atoi(right));
case IFOP_SHR:
return retfloat(atoi(left)>>atoi(right));
case IFOP_ISIN:
return retfloat(!!strstr(right, left));
case IFOP_ISNOTIN:
return retfloat(!strstr(right, left));
case IFOP_LT:
return retfloat(atof(left)<atof(right));
case IFOP_LE:
return retfloat(atof(left)<=atof(right));
case IFOP_GT:
return retfloat(atof(left)>atof(right));
case IFOP_GE:
return retfloat(atof(left)>=atof(right));
case IFOP_EQ:
if (is_numeric(left) && is_numeric(right))
return retfloat(atof(left) == atof(right));
else else
return retfloat((int)atof(s2)%level); return retfloat(!strcmp(left, right));
} case IFOP_NE:
if (!strcmp(com_token, "&")) //and if (is_numeric(left) && is_numeric(right))
{ return retfloat(atof(left) != atof(right));
func=COM_ParseToken(s, IFPUNCT);
if (*com_token == '&')
return retfloat(is_true(s2)&&is_true(If_Token(func, end)));
else else
return retfloat(atoi(s2)&atoi(If_Token(s, end))); return retfloat(!!strcmp(left, right));
} case IFOP_BA:
if (!strcmp(com_token, "div")) //qw262 compatability return retfloat(atoi(left)&atoi(right));
return retfloat(atof(s2)/atof(If_Token(s, end))); case IFOP_XOR:
if (!strcmp(com_token, "or")) //qw262 compatability return retfloat(atoi(left)^atoi(right));
return retfloat(atoi(s2)|atoi(If_Token(s, end))); case IFOP_BO:
if (!strcmp(com_token, "xor")) //qw262 compatability return retfloat(atoi(left)|atoi(right));
return retfloat(atoi(s2)^atoi(If_Token(s, end))); case IFOP_LA:
if (!strcmp(com_token, "and")) //qw262 compatability return retfloat(is_true(left)&&is_true(right));
return retfloat(atoi(s2)&atoi(If_Token(s, end))); case IFOP_LO:
if (!strcmp(com_token, "|")) //or return retfloat(is_true(left)||is_true(right));
{ default:
func=COM_ParseToken(s, IFPUNCT); return retfloat(0);
if (*com_token == '|')
return retfloat(is_true(s2)||is_true(If_Token(func, end)));
else
return retfloat(atoi(s2)|atoi(If_Token(s, end)));
} }
}
static const char *If_Token(const char *func, const char **end, int pri)
{
const char *s, *s2;
int i;
if (pri > 0)
s2 = If_Token(func, &s, pri-1);
else
s2 = If_Token_Term(func, &s);
*end = s;
while (*s == ' ' || *s == '\t')
s++;
for (i = 0; i < countof(ifops); i++)
{
if (!strncmp(s, ifops[i].opname, ifops[i].opnamelen))
{
if (pri == ifops[i].pri)
{
s = If_Token(s + ifops[i].opnamelen, end, pri);
s2 = If_Operator(ifops[i].op, s2, s);
}
break;
}
}
return s2; return s2;
} }
@ -2627,7 +2694,7 @@ qboolean If_EvaluateBoolean(const char *text, int restriction)
tempstack_t *ts = If_Token_GetMark(); tempstack_t *ts = If_Token_GetMark();
int restore = Cmd_ExecLevel; int restore = Cmd_ExecLevel;
Cmd_ExecLevel = restriction; Cmd_ExecLevel = restriction;
text = If_Token(text, &end); text = If_Token(text, &end, IF_PRI_MAX);
ret = is_true(text); ret = is_true(text);
If_Token_Clear(ts); If_Token_Clear(ts);
Cmd_ExecLevel = restore; Cmd_ExecLevel = restore;
@ -2767,7 +2834,7 @@ void Cmd_if_f(void)
elseif: elseif:
// Con_Printf("if %s\n", text); // Con_Printf("if %s\n", text);
for(ret = If_Token(text, (const char **)&end); *ret; ret++) {if (*ret != '0' && *ret != '.')break;} ret = If_Token(text, (const char **)&end, IF_PRI_MAX);
if (!end) if (!end)
{ {
Con_TPrintf("Not terminated\n"); Con_TPrintf("Not terminated\n");
@ -2938,7 +3005,7 @@ void Cmd_set_f(void)
{ {
Cmd_ShiftArgs(1, false); Cmd_ShiftArgs(1, false);
text = Cmd_Args(); text = Cmd_Args();
if (*text == '\"' || (*text == '\\' && text[1] == '\"')) //if it's already quoted, dequote it, and ignore trailing stuff, for q2/q3 compatability if (!docalc && (*text == '\"' || (*text == '\\' && text[1] == '\"'))) //if it's already quoted, dequote it, and ignore trailing stuff, for q2/q3 compatability
text = Cmd_Argv(1); text = Cmd_Argv(1);
else else
{ {
@ -2990,18 +3057,18 @@ void Cmd_set_f(void)
else else
{ {
if (docalc) if (docalc)
text = If_Token(text, &end); text = If_Token(text, &end, IF_PRI_MAX);
Cvar_Set(var, text); Cvar_Set(var, text);
var->flags |= CVAR_USERCREATED | forceflags; var->flags |= CVAR_USERCREATED | forceflags;
if (!stricmp(Cmd_Argv(0), "seta")) if (!strncmp(Cmd_Argv(0), "seta", 4))
var->flags |= CVAR_ARCHIVE; var->flags |= CVAR_ARCHIVE;
} }
} }
else else
{ {
if (docalc) if (docalc)
text = If_Token(text, &end); text = If_Token(text, &end, IF_PRI_MAX);
if (Cmd_FromGamecode()) if (Cmd_FromGamecode())
{ {
var = Cvar_Get(Cmd_Argv(1), "", 0, "Game variables"); var = Cvar_Get(Cmd_Argv(1), "", 0, "Game variables");
@ -3013,7 +3080,7 @@ void Cmd_set_f(void)
} }
if (var && !Cmd_FromGamecode()) if (var && !Cmd_FromGamecode())
if (!stricmp(Cmd_Argv(0), "seta")) if (!strncmp(Cmd_Argv(0), "seta", 4))
var->flags |= CVAR_ARCHIVE|CVAR_USERCREATED; var->flags |= CVAR_ARCHIVE|CVAR_USERCREATED;
If_Token_Clear(mark); If_Token_Clear(mark);

View File

@ -2035,6 +2035,7 @@ static float PlaneNearest(vec3_t normal, vec3_t mins, vec3_t maxs)
return result; return result;
} }
void CLQ1_DrawLine(shader_t *shader, vec3_t v1, vec3_t v2, float r, float g, float b, float a);
qboolean Mod_Trace_Trisoup(vecV_t *posedata, index_t *indexes, int numindexes, vec3_t start, vec3_t end, vec3_t mins, vec3_t maxs, trace_t *trace) qboolean Mod_Trace_Trisoup(vecV_t *posedata, index_t *indexes, int numindexes, vec3_t start, vec3_t end, vec3_t mins, vec3_t maxs, trace_t *trace)
{ {
qboolean impacted = false; qboolean impacted = false;
@ -2053,13 +2054,21 @@ qboolean Mod_Trace_Trisoup(vecV_t *posedata, index_t *indexes, int numindexes, v
float frac; float frac;
vec3_t impactpoint; vec3_t impactpoint;
shader_t *lineshader = NULL;
for (i = 0; i < numindexes; i+=3) for (i = 0; i < numindexes; i+=3)
{ {
p1 = posedata[indexes[i+0]]; p1 = posedata[indexes[i+0]];
p2 = posedata[indexes[i+1]]; p2 = posedata[indexes[i+1]];
p3 = posedata[indexes[i+2]]; p3 = posedata[indexes[i+2]];
/*
VectorAdd(p1, r_refdef.pvsorigin, edge1);
VectorAdd(p2, r_refdef.pvsorigin, edge2);
VectorAdd(p3, r_refdef.pvsorigin, edge3);
CLQ1_DrawLine(lineshader, edge1, edge2, 0, 0, 1, 1);
CLQ1_DrawLine(lineshader, edge2, edge3, 0, 0, 1, 1);
CLQ1_DrawLine(lineshader, edge3, edge1, 0, 0, 1, 1);
*/
VectorSubtract(p1, p2, edge1); VectorSubtract(p1, p2, edge1);
VectorSubtract(p3, p2, edge2); VectorSubtract(p3, p2, edge2);
CrossProduct(edge1, edge2, normal); CrossProduct(edge1, edge2, normal);
@ -2164,6 +2173,25 @@ qboolean Mod_Trace_Trisoup(vecV_t *posedata, index_t *indexes, int numindexes, v
// if (fabs(normal[0]) != 1 && fabs(normal[1]) != 1 && fabs(normal[2]) != 1) // if (fabs(normal[0]) != 1 && fabs(normal[1]) != 1 && fabs(normal[2]) != 1)
// Con_Printf("Non-axial impact\n"); // Con_Printf("Non-axial impact\n");
/* if (!lineshader)
lineshader = R_RegisterShader("lineshader", SUF_NONE,
"{\n"
"polygonoffset\n"
"{\n"
"map $whiteimage\n"
"blendfunc add\n"
"rgbgen vertex\n"
"alphagen vertex\n"
"}\n"
"}\n");
VectorAdd(p1, r_refdef.pvsorigin, edge1);
VectorAdd(p2, r_refdef.pvsorigin, edge2);
VectorAdd(p3, r_refdef.pvsorigin, edge3);
CLQ1_DrawLine(lineshader, edge1, edge2, 0, 1, 0, 1);
CLQ1_DrawLine(lineshader, edge2, edge3, 0, 1, 0, 1);
CLQ1_DrawLine(lineshader, edge3, edge1, 0, 1, 0, 1);
*/
} }
return impacted; return impacted;
} }
@ -2199,20 +2227,31 @@ qboolean Mod_Trace(model_t *model, int forcehullnum, int frame, vec3_t axis[3],
VectorCopy(end, end_l); VectorCopy(end, end_l);
} }
while(mod) trace->fraction = trace->truefraction = 1;
for(; mod; mod = mod->nextsurf, surfnum++)
{ {
indexes = mod->ofs_indexes; indexes = mod->ofs_indexes;
#ifdef SKELETALMODELS
if (!mod->numanimations) if (!mod->numanimations)
{ {
#ifdef SKELETALMODELS
//certain models have no possibility of animation. //certain models have no possibility of animation.
//fixme: skeletal objects...
if (mod->ofs_skel_xyz)
posedata = mod->ofs_skel_xyz; posedata = mod->ofs_skel_xyz;
}
else else
#endif #endif
continue;
}
else
{ {
group = mod->ofsanimations; group = mod->ofsanimations;
pose = group[0].poseofs; group += frame % mod->numanimations;
//FIXME: no support for frame blending.
if (!group->numposes)
continue;
pose = group->poseofs;
pose += 0%group->numposes; //FIXME: no framegroup support
posedata = pose->ofsverts; posedata = pose->ofsverts;
#ifdef SKELETALMODELS #ifdef SKELETALMODELS
if (mod->numbones && mod->shares_verts != cursurfnum) if (mod->numbones && mod->shares_verts != cursurfnum)
@ -2259,9 +2298,6 @@ qboolean Mod_Trace(model_t *model, int forcehullnum, int frame, vec3_t axis[3],
trace->endpos[1] = start[1] + trace->fraction*(end[1] - start[1]); trace->endpos[1] = start[1] + trace->fraction*(end[1] - start[1]);
trace->endpos[2] = start[2] + trace->fraction*(end[2] - start[2]); trace->endpos[2] = start[2] + trace->fraction*(end[2] - start[2]);
} }
mod = mod->nextsurf;
surfnum++;
} }
trace->allsolid = false; trace->allsolid = false;

View File

@ -400,10 +400,19 @@ void R_RenderDlights (void)
/*coronas use depth testing to compute visibility*/ /*coronas use depth testing to compute visibility*/
if (coronastyle) if (coronastyle)
{
extern cvar_t temp1;
if (r_coronas_occlusion.ival)
{
if (TraceLineR(r_refdef.vieworg, l->origin, waste1, waste2))
continue;
}
else
{ {
if (TraceLineN(r_refdef.vieworg, l->origin, waste1, waste2)) if (TraceLineN(r_refdef.vieworg, l->origin, waste1, waste2))
continue; continue;
} }
}
if (!R_BuildDlightMesh (l, intensity, cscale, coronastyle) && !coronastyle) if (!R_BuildDlightMesh (l, intensity, cscale, coronastyle) && !coronastyle)
AddLightBlend (l->color[0], l->color[1], l->color[2], l->radius * 0.0003); AddLightBlend (l->color[0], l->color[1], l->color[2], l->radius * 0.0003);

View File

@ -158,6 +158,7 @@ static struct
char *(*pXSetLocaleModifiers)(char *modifier_list); char *(*pXSetLocaleModifiers)(char *modifier_list);
Bool (*pXSupportsLocale)(void); Bool (*pXSupportsLocale)(void);
XIM (*pXOpenIM)(Display *display, struct _XrmHashBucketRec *db, char *res_name, char *res_class); XIM (*pXOpenIM)(Display *display, struct _XrmHashBucketRec *db, char *res_name, char *res_class);
char * (*pXGetIMValues)(XIM im, ...);
XIC (*pXCreateIC)(XIM im, ...); XIC (*pXCreateIC)(XIM im, ...);
void (*pXSetICFocus)(XIC ic); void (*pXSetICFocus)(XIC ic);
char * (*pXGetICValues)(XIC ic, ...); char * (*pXGetICValues)(XIC ic, ...);
@ -247,6 +248,7 @@ static qboolean x11_initlib(void)
x11.pXSetLocaleModifiers = Sys_GetAddressForName(x11.lib, "XSetLocaleModifiers"); x11.pXSetLocaleModifiers = Sys_GetAddressForName(x11.lib, "XSetLocaleModifiers");
x11.pXSupportsLocale = Sys_GetAddressForName(x11.lib, "XSupportsLocale"); x11.pXSupportsLocale = Sys_GetAddressForName(x11.lib, "XSupportsLocale");
x11.pXOpenIM = Sys_GetAddressForName(x11.lib, "XOpenIM"); x11.pXOpenIM = Sys_GetAddressForName(x11.lib, "XOpenIM");
x11.pXGetIMValues = Sys_GetAddressForName(x11.lib, "XGetIMValues");
x11.pXCreateIC = Sys_GetAddressForName(x11.lib, "XCreateIC"); x11.pXCreateIC = Sys_GetAddressForName(x11.lib, "XCreateIC");
x11.pXSetICFocus = Sys_GetAddressForName(x11.lib, "XSetICFocus"); x11.pXSetICFocus = Sys_GetAddressForName(x11.lib, "XSetICFocus");
x11.pXGetICValues = Sys_GetAddressForName(x11.lib, "XGetICValues"); x11.pXGetICValues = Sys_GetAddressForName(x11.lib, "XGetICValues");
@ -601,7 +603,7 @@ static long X_InitUnicode(void)
if (!COM_CheckParm("-noxim")) if (!COM_CheckParm("-noxim"))
{ {
if (x11.pXSetLocaleModifiers && x11.pXSupportsLocale && x11.pXOpenIM && x11.pXCreateIC && x11.pXSetICFocus && x11.pXGetICValues && x11.pXFilterEvent && (x11.pXutf8LookupString || x11.pXwcLookupString) && x11.pXDestroyIC && x11.pXCloseIM) if (x11.pXSetLocaleModifiers && x11.pXSupportsLocale && x11.pXOpenIM && x11.pXGetIMValues && x11.pXCreateIC && x11.pXSetICFocus && x11.pXGetICValues && x11.pXFilterEvent && (x11.pXutf8LookupString || x11.pXwcLookupString) && x11.pXDestroyIC && x11.pXCloseIM)
{ {
setlocale(LC_CTYPE, ""); //just in case. setlocale(LC_CTYPE, ""); //just in case.
x11.pXSetLocaleModifiers(""); x11.pXSetLocaleModifiers("");
@ -609,9 +611,38 @@ static long X_InitUnicode(void)
{ {
x11.inputmethod = x11.pXOpenIM(vid_dpy, NULL, NULL, NULL); x11.inputmethod = x11.pXOpenIM(vid_dpy, NULL, NULL, NULL);
if (x11.inputmethod) if (x11.inputmethod)
{
XIMStyles *sup = NULL;
XIMStyle st = 0;
int i;
x11.pXGetIMValues(x11.inputmethod, XNQueryInputStyle, &sup, NULL);
for (i = 0; sup && i < sup->count_styles; i++)
{ //each style will have one of each bis set.
#define prestyles (XIMPreeditNothing|XIMPreeditNone)
#define statusstyles (XIMStatusNothing|XIMStatusNone)
#define supstyles (prestyles|statusstyles)
if ((sup->supported_styles[i] & supstyles) != sup->supported_styles[i])
continue;
if ((st & prestyles) != (sup->supported_styles[i] & prestyles))
{
if ((sup->supported_styles[i] & XIMPreeditNothing) && !(st & XIMPreeditNothing))
st = sup->supported_styles[i];
else if ((sup->supported_styles[i] & XIMPreeditNone) && !(st & (XIMPreeditNone|XIMPreeditNothing)))
st = sup->supported_styles[i];
}
else
{
if ((sup->supported_styles[i] & XIMStatusNothing) && !(st & XIMStatusNothing))
st = sup->supported_styles[i];
else if ((sup->supported_styles[i] & XIMStatusNone) && !(st & (XIMStatusNone|XIMStatusNothing)))
st = sup->supported_styles[i];
}
}
x11.pXFree(sup);
if (st != 0)
{ {
x11.unicodecontext = x11.pXCreateIC(x11.inputmethod, x11.unicodecontext = x11.pXCreateIC(x11.inputmethod,
XNInputStyle, XIMPreeditNothing | XIMStatusNothing, XNInputStyle, st,
XNClientWindow, vid_window, XNClientWindow, vid_window,
XNFocusWindow, vid_window, XNFocusWindow, vid_window,
NULL); NULL);
@ -624,7 +655,8 @@ static long X_InitUnicode(void)
} }
} }
} }
// setlocale(LC_CTYPE, "C"); }
setlocale(LC_CTYPE, "C");
} }
} }

View File

@ -588,6 +588,7 @@ extern pbool flag_filetimes;
extern pbool flag_typeexplicit; extern pbool flag_typeexplicit;
extern pbool flag_noboundchecks; extern pbool flag_noboundchecks;
extern pbool flag_brokenarrays; extern pbool flag_brokenarrays;
extern pbool flag_rootconstructor;
extern pbool flag_guiannotate; extern pbool flag_guiannotate;
extern pbool opt_overlaptemps; extern pbool opt_overlaptemps;

View File

@ -106,6 +106,7 @@ pbool flag_typeexplicit; //no implicit type conversions, you must do the casts y
pbool flag_noboundchecks; //Disable generation of bound check instructions. pbool flag_noboundchecks; //Disable generation of bound check instructions.
pbool flag_guiannotate; pbool flag_guiannotate;
pbool flag_brokenarrays; //return array; returns array[0] instead of &array; pbool flag_brokenarrays; //return array; returns array[0] instead of &array;
pbool flag_rootconstructor; //if true, class constructors are ordered to call the super constructor first, rather than the child constructor
pbool opt_overlaptemps; //reduce numpr_globals by reuse of temps. When they are not needed they are freed for reuse. The way this is implemented is better than frikqcc's. (This is the single most important optimisation) pbool opt_overlaptemps; //reduce numpr_globals by reuse of temps. When they are not needed they are freed for reuse. The way this is implemented is better than frikqcc's. (This is the single most important optimisation)
pbool opt_assignments; //STORE_F isn't used if an operation wrote to a temp. pbool opt_assignments; //STORE_F isn't used if an operation wrote to a temp.
@ -5935,9 +5936,11 @@ void QCC_PR_EmitClassFromFunction(QCC_def_t *scope, QCC_type_t *basetype)
QCC_type_t *parenttype; QCC_type_t *parenttype;
QCC_sref_t ed; QCC_sref_t ed;
QCC_sref_t constructor = nullsref; QCC_sref_t constructor;
int basictypefield[ev_union+1]; int basictypefield[ev_union+1];
int src,dst;
// int func; // int func;
if (numfunctions >= MAX_FUNCTIONS) if (numfunctions >= MAX_FUNCTIONS)
@ -5972,8 +5975,7 @@ void QCC_PR_EmitClassFromFunction(QCC_def_t *scope, QCC_type_t *basetype)
QCC_PR_EmitClassFunctionTable(basetype, basetype, ed); QCC_PR_EmitClassFunctionTable(basetype, basetype, ed);
//FIXME: these constructors are called in the wrong order src = numstatements;
constructor = nullsref;
for (parenttype = basetype; parenttype; parenttype = parenttype->parentclass) for (parenttype = basetype; parenttype; parenttype = parenttype->parentclass)
{ {
char membername[2048]; char membername[2048];
@ -5981,22 +5983,25 @@ void QCC_PR_EmitClassFromFunction(QCC_def_t *scope, QCC_type_t *basetype)
constructor = QCC_PR_GetSRef(NULL, membername, NULL, false, 0, false); constructor = QCC_PR_GetSRef(NULL, membername, NULL, false, 0, false);
if (constructor.cast) if (constructor.cast)
{ //self = ent; {
// self = QCC_PR_GetDef(type_entity, "self", NULL, false, 0, false);
// oself = QCC_PR_GetDef(type_entity, "oself", scope, !constructed, 0, false);
// if (!constructed)
// {
// QCC_FreeTemp(QCC_PR_Statement(&pr_opcodes[OP_STORE_ENT], self, oself, NULL));
// constructed = true;
// }
constructor.sym->referenced = true; constructor.sym->referenced = true;
// QCC_FreeTemp(QCC_PR_Statement(&pr_opcodes[OP_STORE_ENT], ed, self, NULL)); //return to our old self.
QCC_PR_SimpleStatement(&pr_opcodes[OP_CALL0], constructor, nullsref, nullsref, false); QCC_PR_SimpleStatement(&pr_opcodes[OP_CALL0], constructor, nullsref, nullsref, false);
QCC_FreeTemp(constructor); QCC_FreeTemp(constructor);
} }
} }
// if (constructed)
// QCC_FreeTemp(QCC_PR_Statement(&pr_opcodes[OP_STORE_ENT], oself, self, NULL)); if (flag_rootconstructor)
{
dst = numstatements-1;
while(src < dst)
{
QCC_sref_t t = statements[src].a;
statements[src].a = statements[dst].a;
statements[dst].a = t;
src++;
dst--;
}
}
QCC_FreeTemp(QCC_PR_Statement(&pr_opcodes[OP_DONE], nullsref, nullsref, NULL)); QCC_FreeTemp(QCC_PR_Statement(&pr_opcodes[OP_DONE], nullsref, nullsref, NULL));

View File

@ -330,6 +330,7 @@ compiler_flag_t compiler_flag[] = {
{&flag_ifvector, FLAG_MIDCOMPILE|FLAG_ASDEFAULT,"ifvector","if('0 1 0') fix","Fixes conditional vector logic."}, {&flag_ifvector, FLAG_MIDCOMPILE|FLAG_ASDEFAULT,"ifvector","if('0 1 0') fix","Fixes conditional vector logic."},
{&flag_vectorlogic, FLAG_MIDCOMPILE|FLAG_ASDEFAULT,"vectorlogic","v&&v||v fix", "Fixes conditional vector logic."}, {&flag_vectorlogic, FLAG_MIDCOMPILE|FLAG_ASDEFAULT,"vectorlogic","v&&v||v fix", "Fixes conditional vector logic."},
{&flag_brokenarrays, FLAG_MIDCOMPILE,"brokenarray", "array[0] omission", "Treat references to arrays as references to the first index of said array, to replicate an old fteqcc bug."}, {&flag_brokenarrays, FLAG_MIDCOMPILE,"brokenarray", "array[0] omission", "Treat references to arrays as references to the first index of said array, to replicate an old fteqcc bug."},
{&flag_rootconstructor, FLAG_MIDCOMPILE,"rootconstructor","root constructor first", "When enabled, the root constructor should be called first like in c++."},
{&flag_acc, 0, "acc", "Reacc support", "Reacc is a pascall like compiler. It was released before the Quake source was released. This flag has a few effects. It sorts all qc files in the current directory into alphabetical order to compile them. It also allows Reacc global/field distinctions, as well as allows ¦ as EOF. Whilst case insensitivity and lax type checking are supported by reacc, they are seperate compiler flags in fteqcc."}, //reacc like behaviour of src files. {&flag_acc, 0, "acc", "Reacc support", "Reacc is a pascall like compiler. It was released before the Quake source was released. This flag has a few effects. It sorts all qc files in the current directory into alphabetical order to compile them. It also allows Reacc global/field distinctions, as well as allows ¦ as EOF. Whilst case insensitivity and lax type checking are supported by reacc, they are seperate compiler flags in fteqcc."}, //reacc like behaviour of src files.
{&flag_caseinsensitive, 0, "caseinsens", "Case insensitivity", "Causes fteqcc to become case insensitive whilst compiling names. It's generally not advised to use this as it compiles a little more slowly and provides little benefit. However, it is required for full reacc support."}, //symbols will be matched to an insensitive case if the specified case doesn't exist. This should b usable for any mod {&flag_caseinsensitive, 0, "caseinsens", "Case insensitivity", "Causes fteqcc to become case insensitive whilst compiling names. It's generally not advised to use this as it compiles a little more slowly and provides little benefit. However, it is required for full reacc support."}, //symbols will be matched to an insensitive case if the specified case doesn't exist. This should b usable for any mod
{&flag_laxcasts, FLAG_MIDCOMPILE,"lax", "Lax type checks", "Disables many errors (generating warnings instead) when function calls or operations refer to two normally incompatible types. This is required for reacc support, and can also allow certain (evil) mods to compile that were originally written for frikqcc."}, //Allow lax casting. This'll produce loadsa warnings of course. But allows compilation of certain dodgy code. {&flag_laxcasts, FLAG_MIDCOMPILE,"lax", "Lax type checks", "Disables many errors (generating warnings instead) when function calls or operations refer to two normally incompatible types. This is required for reacc support, and can also allow certain (evil) mods to compile that were originally written for frikqcc."}, //Allow lax casting. This'll produce loadsa warnings of course. But allows compilation of certain dodgy code.

View File

@ -351,7 +351,6 @@ struct
static const char *q1qvmentstring; static const char *q1qvmentstring;
static vm_t *q1qvm; static vm_t *q1qvm;
static pubprogfuncs_t q1qvmprogfuncs; static pubprogfuncs_t q1qvmprogfuncs;
static edict_t **q1qvmedicttable;
static void *evars; //pointer to the gamecodes idea of an edict_t static void *evars; //pointer to the gamecodes idea of an edict_t
@ -377,10 +376,10 @@ static edict_t *QDECL Q1QVMPF_EdictNum(pubprogfuncs_t *pf, unsigned int num)
if (/*num < 0 ||*/ num >= sv.world.max_edicts) if (/*num < 0 ||*/ num >= sv.world.max_edicts)
return NULL; return NULL;
e = q1qvmedicttable[num]; e = q1qvmprogfuncs.edicttable[num];
if (!e) if (!e)
{ {
e = q1qvmedicttable[num] = Z_TagMalloc(sizeof(edict_t)+sizeof(extentvars_t), VMFSID_Q1QVM); e = q1qvmprogfuncs.edicttable[num] = Z_TagMalloc(sizeof(edict_t)+sizeof(extentvars_t), VMFSID_Q1QVM);
e->v = (stdentvars_t*)((char*)evars + (num * sv.world.edict_size) + WASTED_EDICT_T_SIZE); e->v = (stdentvars_t*)((char*)evars + (num * sv.world.edict_size) + WASTED_EDICT_T_SIZE);
e->xv = (extentvars_t*)(e+1); e->xv = (extentvars_t*)(e+1);
e->entnum = num; e->entnum = num;
@ -468,7 +467,7 @@ static edict_t *QDECL Q1QVMPF_EntAlloc(pubprogfuncs_t *pf)
} }
sv.world.num_edicts++; sv.world.num_edicts++;
e = (edict_t*)EDICT_NUM(pf, i); e = (edict_t*)Q1QVMPF_EdictNum(pf, i);
// new ents come ready wiped // new ents come ready wiped
// Q1QVMED_ClearEdict (e, false); // Q1QVMED_ClearEdict (e, false);
@ -602,7 +601,7 @@ static qintptr_t QVM_Remove_Ent (void *offset, quintptr_t mask, const qintptr_t
{ {
if (arg[0] >= sv.world.max_edicts) if (arg[0] >= sv.world.max_edicts)
return false; return false;
Q1QVMPF_EntRemove(svprogfuncs, q1qvmedicttable[arg[0]]); Q1QVMPF_EntRemove(svprogfuncs, q1qvmprogfuncs.edicttable[arg[0]]);
return true; return true;
} }
@ -1172,7 +1171,7 @@ static qintptr_t QVM_Find (void *offset, quintptr_t mask, const qintptr_t *arg)
match = ""; match = "";
for (i = first+1; i < sv.world.num_edicts; i++) for (i = first+1; i < sv.world.num_edicts; i++)
{ {
e = q1qvmedicttable[i]; e = q1qvmprogfuncs.edicttable[i];
field = VM_POINTER(*((string_t*)e->v + ofs/4)); field = VM_POINTER(*((string_t*)e->v + ofs/4));
if (field == NULL) if (field == NULL)
{ {
@ -1713,10 +1712,10 @@ void Q1QVM_Shutdown(void)
if (svprogfuncs == &q1qvmprogfuncs) if (svprogfuncs == &q1qvmprogfuncs)
sv.world.progs = svprogfuncs = NULL; sv.world.progs = svprogfuncs = NULL;
Z_FreeTags(VMFSID_Q1QVM); Z_FreeTags(VMFSID_Q1QVM);
if (q1qvmedicttable) if (q1qvmprogfuncs.edicttable)
{ {
Z_Free(q1qvmedicttable); Z_Free(q1qvmprogfuncs.edicttable);
q1qvmedicttable = NULL; q1qvmprogfuncs.edicttable = NULL;
} }
} }
} }
@ -1821,7 +1820,7 @@ qboolean PR_LoadQ1QVM(void)
sv.world.max_edicts = 0; //so clear these out, just in case sv.world.max_edicts = 0; //so clear these out, just in case
sv.world.edict_size = 0; //if we get a division by zero, then at least its a safe crash sv.world.edict_size = 0; //if we get a division by zero, then at least its a safe crash
q1qvmedicttable = NULL; q1qvmprogfuncs.edicttable = NULL;
q1qvmprogfuncs.stringtable = VM_MemoryBase(q1qvm); q1qvmprogfuncs.stringtable = VM_MemoryBase(q1qvm);
@ -1852,7 +1851,7 @@ qboolean PR_LoadQ1QVM(void)
sv.world.num_edicts = 1; sv.world.num_edicts = 1;
sv.world.max_edicts = bound(64, pr_maxedicts.ival, MAX_EDICTS); sv.world.max_edicts = bound(64, pr_maxedicts.ival, MAX_EDICTS);
q1qvmedicttable = Z_Malloc(sizeof(*q1qvmedicttable) * sv.world.max_edicts); q1qvmprogfuncs.edicttable = Z_Malloc(sizeof(*q1qvmprogfuncs.edicttable) * sv.world.max_edicts);
limit = VM_MemoryMask(q1qvm); limit = VM_MemoryMask(q1qvm);
if (gd->sizeofent < 0 || gd->sizeofent > (0xffffffff-(qintptr_t)gd->ents) / sv.world.max_edicts) if (gd->sizeofent < 0 || gd->sizeofent > (0xffffffff-(qintptr_t)gd->ents) / sv.world.max_edicts)
@ -1941,7 +1940,7 @@ qboolean PR_LoadQ1QVM(void)
sv.world.progs = &q1qvmprogfuncs; sv.world.progs = &q1qvmprogfuncs;
sv.world.edicts = (wedict_t*)EDICT_NUM(svprogfuncs, 0); sv.world.edicts = (wedict_t*)Q1QVMPF_EdictNum(svprogfuncs, 0);
sv.world.usesolidcorpse = true; sv.world.usesolidcorpse = true;
if ((unsigned)gd->global->mapname && (unsigned)gd->global->mapname+MAPNAME_LEN < VM_MemoryMask(q1qvm)) if ((unsigned)gd->global->mapname && (unsigned)gd->global->mapname+MAPNAME_LEN < VM_MemoryMask(q1qvm))

View File

@ -288,7 +288,7 @@ void World_ClearWorld (world_t *w)
w->areanodes = Z_Malloc(sizeof(*w->areanodes) * pow(2, w->areanodedepth+1)); w->areanodes = Z_Malloc(sizeof(*w->areanodes) * pow(2, w->areanodedepth+1));
} }
else else
memset (w->areanodes, 0, sizeof(w->areanodes)); memset (w->areanodes, 0, sizeof(*w->areanodes)*w->numareanodes);
w->numareanodes = 0; w->numareanodes = 0;
World_CreateAreaNode (w, 0, mins, maxs); World_CreateAreaNode (w, 0, mins, maxs);
} }