Fixed x64 script/class connections and added material flags that are needed.

This commit is contained in:
Justin Marshall
2026-05-05 16:20:05 -07:00
parent 8d5f678b25
commit d06356e042
12 changed files with 2437 additions and 2202 deletions
+4 -4
View File
@@ -60,10 +60,10 @@ typedef enum {
} traceModel_t;
// these are bit cache limits
#define MAX_TRACEMODEL_VERTS 32
#define MAX_TRACEMODEL_EDGES 32
#define MAX_TRACEMODEL_POLYS 16
#define MAX_TRACEMODEL_POLYEDGES 16
#define MAX_TRACEMODEL_VERTS 64
#define MAX_TRACEMODEL_EDGES 64
#define MAX_TRACEMODEL_POLYS 32
#define MAX_TRACEMODEL_POLYEDGES 32
typedef idVec3 traceModelVert_t;
File diff suppressed because it is too large Load Diff
+21 -39
View File
@@ -12,7 +12,6 @@ instancing of objects.
#include "../Game_local.h"
/***********************************************************************
idTypeInfo
@@ -882,7 +881,7 @@ idClass::ProcessEventArgs
bool idClass::ProcessEventArgs( const idEventDef *ev, int numargs, ... ) {
idTypeInfo *c;
int num;
int data[ D_EVENT_MAXARGS ];
intptr_t data[ D_EVENT_MAXARGS ];
va_list args;
assert( ev );
@@ -990,106 +989,89 @@ bool idClass::ProcessEvent( const idEventDef *ev, idEventArg arg1, idEventArg ar
idClass::ProcessEventArgPtr
================
*/
bool idClass::ProcessEventArgPtr( const idEventDef *ev, int *data ) {
bool idClass::ProcessEventArgPtr( const idEventDef *ev, intptr_t*data ) {
idTypeInfo* c;
int num;
eventCallback_t callback;
assert(ev);
assert(idEvent::initialized);
if (g_debugTriggers.GetBool() && (ev == &EV_Activate) && IsType(idEntity::Type)) {
const idEntity* ent = *reinterpret_cast<idEntity**>(data);
gameLocal.Printf("%d: '%s' activated by '%s'\n", gameLocal.framenum, static_cast<idEntity*>(this)->GetName(), ent ? ent->GetName() : "NULL");
}
c = GetType();
num = ev->GetEventNum();
if (!c->eventMap[num]) {
// we don't respond to this event, so ignore it
return false;
}
callback = c->eventMap[num];
#if !CPU_EASYARGS
// RB: I tried first to get CPU_EASYARGS switch running with x86_64
// but it caused many crashes with the Doom scripts.
// The new Callbacks.cpp was generated with intptr_t and it works fine.
#if CPU_EASYARGS
/*
on ppc architecture, floats are passed in a seperate set of registers
on ppc architecture, floats are passed in a separate set of registers
the function prototypes must have matching float declaration
http://developer.apple.com/documentation/DeveloperTools/Conceptual/MachORuntime/2rt_powerpc_abi/chapter_9_section_5.html
*/
switch( ev->GetFormatspecIndex() ) {
switch (ev->GetFormatspecIndex())
{
case 1 << D_EVENT_MAXARGS:
(this->*callback)();
break;
// generated file - see CREATE_EVENT_CODE
#include "Callbacks.cpp"
default:
gameLocal.Warning("Invalid formatspec on event '%s'", ev->GetName());
break;
}
#else
assert(D_EVENT_MAXARGS == 8);
switch( ev->GetNumArgs() ) {
// RB: 64 bit fixes, changed int to intptr_t
switch (ev->GetNumArgs())
{
case 0:
(this->*callback)();
break;
case 1:
typedef void ( idClass::*eventCallback_1_t )( const int );
typedef void (idClass::* eventCallback_1_t)(const intptr_t);
(this->*(eventCallback_1_t)callback)(data[0]);
break;
case 2:
typedef void ( idClass::*eventCallback_2_t )( const int, const int );
typedef void (idClass::* eventCallback_2_t)(const intptr_t, const intptr_t);
(this->*(eventCallback_2_t)callback)(data[0], data[1]);
break;
case 3:
typedef void ( idClass::*eventCallback_3_t )( const int, const int, const int );
typedef void (idClass::* eventCallback_3_t)(const intptr_t, const intptr_t, const intptr_t);
(this->*(eventCallback_3_t)callback)(data[0], data[1], data[2]);
break;
case 4:
typedef void ( idClass::*eventCallback_4_t )( const int, const int, const int, const int );
typedef void (idClass::* eventCallback_4_t)(const intptr_t, const intptr_t, const intptr_t, const intptr_t);
(this->*(eventCallback_4_t)callback)(data[0], data[1], data[2], data[3]);
break;
case 5:
typedef void ( idClass::*eventCallback_5_t )( const int, const int, const int, const int, const int );
typedef void (idClass::* eventCallback_5_t)(const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t);
(this->*(eventCallback_5_t)callback)(data[0], data[1], data[2], data[3], data[4]);
break;
case 6:
typedef void ( idClass::*eventCallback_6_t )( const int, const int, const int, const int, const int, const int );
typedef void (idClass::* eventCallback_6_t)(const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t);
(this->*(eventCallback_6_t)callback)(data[0], data[1], data[2], data[3], data[4], data[5]);
break;
case 7:
typedef void ( idClass::*eventCallback_7_t )( const int, const int, const int, const int, const int, const int, const int );
typedef void (idClass::* eventCallback_7_t)(const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t);
(this->*(eventCallback_7_t)callback)(data[0], data[1], data[2], data[3], data[4], data[5], data[6]);
break;
case 8:
typedef void ( idClass::*eventCallback_8_t )( const int, const int, const int, const int, const int, const int, const int, const int );
typedef void (idClass::* eventCallback_8_t)(const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t, const intptr_t);
(this->*(eventCallback_8_t)callback)(data[0], data[1], data[2], data[3], data[4], data[5], data[6], data[7]);
break;
default:
gameLocal.Warning("Invalid formatspec on event '%s'", ev->GetName());
break;
}
// RB end
#endif
return true;
}
+7 -7
View File
@@ -32,17 +32,17 @@ struct idEventFunc {
class idEventArg {
public:
int type;
int value;
intptr_t value;
idEventArg() { type = D_EVENT_INTEGER; value = 0; };
idEventArg( int data ) { type = D_EVENT_INTEGER; value = data; };
idEventArg( float data ) { type = D_EVENT_FLOAT; value = *reinterpret_cast<int *>( &data ); };
//HUMANHEAD: aob - added const to idVec3
idEventArg( const idVec3 &data ) { type = D_EVENT_VECTOR; value = reinterpret_cast<int>( &data ); };
idEventArg( const idStr &data ) { type = D_EVENT_STRING; value = reinterpret_cast<int>( data.c_str() ); };
idEventArg( const char *data ) { type = D_EVENT_STRING; value = reinterpret_cast<int>( data ); };
idEventArg( const class idEntity *data ) { type = D_EVENT_ENTITY; value = reinterpret_cast<int>( data ); };
idEventArg( const struct trace_s *data ) { type = D_EVENT_TRACE; value = reinterpret_cast<int>( data ); };
idEventArg( const idVec3 &data ) { type = D_EVENT_VECTOR; value = reinterpret_cast<intptr_t>( &data ); };
idEventArg( const idStr &data ) { type = D_EVENT_STRING; value = reinterpret_cast<intptr_t>( data.c_str() ); };
idEventArg( const char *data ) { type = D_EVENT_STRING; value = reinterpret_cast<intptr_t>( data ); };
idEventArg( const class idEntity *data ) { type = D_EVENT_ENTITY; value = reinterpret_cast<intptr_t>( data ); };
idEventArg( const struct trace_s *data ) { type = D_EVENT_TRACE; value = reinterpret_cast<intptr_t>( data ); };
};
class idAllocError : public idException {
@@ -206,7 +206,7 @@ public:
bool ProcessEvent( const idEventDef *ev, idEventArg arg1, idEventArg arg2, idEventArg arg3, idEventArg arg4, idEventArg arg5, idEventArg arg6, idEventArg arg7 );
bool ProcessEvent( const idEventDef *ev, idEventArg arg1, idEventArg arg2, idEventArg arg3, idEventArg arg4, idEventArg arg5, idEventArg arg6, idEventArg arg7, idEventArg arg8 );
bool ProcessEventArgPtr( const idEventDef *ev, int *data );
bool ProcessEventArgPtr( const idEventDef *ev, intptr_t*data );
void CancelEvents( const idEventDef *ev );
virtual // HUMANHEAD nla
void Event_Remove( void );
+115 -48
View File
@@ -72,15 +72,21 @@ idEventDef::idEventDef( const char *command, const char *formatspec, char return
switch( formatspec[ i ] ) {
case D_EVENT_FLOAT:
bits |= 1 << i;
argsize += sizeof( float );
// RB: 64 bit fix, changed sizeof( float ) to sizeof( intptr_t )
argsize += sizeof(intptr_t);
// RB end
break;
case D_EVENT_INTEGER:
argsize += sizeof( int );
// RB: 64 bit fix, changed sizeof( int ) to sizeof( intptr_t )
argsize += sizeof(intptr_t);
// RB end
break;
case D_EVENT_VECTOR:
argsize += sizeof( idVec3 );
// RB: 64 bit fix, changed sizeof( idVec3 ) to E_EVENT_SIZEOF_VEC
argsize += E_EVENT_SIZEOF_VEC;
// RB end
break;
case D_EVENT_STRING:
@@ -88,11 +94,15 @@ idEventDef::idEventDef( const char *command, const char *formatspec, char return
break;
case D_EVENT_ENTITY:
argsize += sizeof( idEntityPtr<idEntity> );
// RB: 64 bit fix, sizeof( idEntityPtr<idEntity> ) to sizeof( intptr_t )
argsize += sizeof(intptr_t);
// RB end
break;
case D_EVENT_ENTITY_NULL:
argsize += sizeof( idEntityPtr<idEntity> );
// RB: 64 bit fix, sizeof( idEntityPtr<idEntity> ) to sizeof( intptr_t )
argsize += sizeof(intptr_t);
// RB end
break;
case D_EVENT_TRACE:
@@ -326,7 +336,7 @@ idEvent *idEvent::Alloc( const idEventDef *evdef, int numargs, va_list args ) {
idEvent::CopyArgs
================
*/
void idEvent::CopyArgs( const idEventDef *evdef, int numargs, va_list args, int data[ D_EVENT_MAXARGS ] ) {
void idEvent::CopyArgs( const idEventDef *evdef, int numargs, va_list args, intptr_t data[ D_EVENT_MAXARGS ] ) {
int i;
const char *format;
idEventArg *arg;
@@ -455,7 +465,7 @@ idEvent::ServiceEvents
void idEvent::ServiceEvents( void ) {
idEvent *event;
int num;
int args[ D_EVENT_MAXARGS ];
intptr_t args[ D_EVENT_MAXARGS ];
int offset;
int i;
int numargs;
@@ -635,61 +645,84 @@ void idEvent::Save( idSaveGame *savefile ) {
byte* dataPtr;
bool validTrace;
const char* format;
// RB: for missing D_EVENT_STRING
idStr s;
// RB end
savefile->WriteInt(EventQueue.Num());
event = EventQueue.Next();
while( event != NULL ) {
while (event != NULL)
{
savefile->WriteInt(event->time);
savefile->WriteString(event->eventdef->GetName());
savefile->WriteString(event->typeinfo->classname);
savefile->WriteObject(event->object);
savefile->WriteInt(event->eventdef->GetArgSize());
format = event->eventdef->GetArgFormat();
for ( i = 0, size = 0; i < event->eventdef->GetNumArgs(); ++i) {
for (i = 0, size = 0; i < event->eventdef->GetNumArgs(); ++i)
{
dataPtr = &event->data[event->eventdef->GetArgOffset(i)];
switch( format[ i ] ) {
switch (format[i])
{
case D_EVENT_FLOAT:
savefile->WriteFloat(*reinterpret_cast<float*>(dataPtr));
size += sizeof( float );
// RB: 64 bit fix, changed sizeof( float ) to sizeof( intptr_t )
size += sizeof(intptr_t);
// RB end
break;
case D_EVENT_INTEGER:
// RB: 64 bit fix, changed sizeof( int ) to sizeof( intptr_t )
savefile->WriteInt(*reinterpret_cast<int*>(dataPtr));
size += sizeof(intptr_t);
break;
// RB end
case D_EVENT_ENTITY:
case D_EVENT_ENTITY_NULL:
savefile->WriteInt( *reinterpret_cast<int *>( dataPtr ) );
size += sizeof( int );
// RB: 64 bit fix, changed alignment to sizeof( intptr_t )
reinterpret_cast<idEntityPtr<idEntity>*>(dataPtr)->Save(savefile);
size += sizeof(intptr_t);
// RB end
break;
case D_EVENT_VECTOR:
savefile->WriteVec3(*reinterpret_cast<idVec3*>(dataPtr));
size += sizeof( idVec3 );
// RB: 64 bit fix, changed sizeof( int ) to E_EVENT_SIZEOF_VEC
size += E_EVENT_SIZEOF_VEC;
// RB end
break;
#if 1
// RB: added missing D_EVENT_STRING case
case D_EVENT_STRING:
s.Clear();
s.Append(reinterpret_cast<char*>(dataPtr));
savefile->WriteString(s);
//size += s.Length();
size += MAX_STRING_LEN;
break;
// RB end
#endif
case D_EVENT_TRACE:
validTrace = *reinterpret_cast<bool*>(dataPtr);
savefile->WriteBool(validTrace);
size += sizeof(bool);
if ( validTrace ) {
if (validTrace)
{
size += sizeof(trace_t);
const trace_t& t = *reinterpret_cast<trace_t*>(dataPtr + sizeof(bool));
SaveTrace(savefile, t);
if ( t.c.material ) {
if (t.c.material)
{
size += MAX_STRING_LEN;
str = reinterpret_cast<char*>(dataPtr + sizeof(bool) + sizeof(trace_t));
savefile->Write(str, MAX_STRING_LEN);
}
}
break;
// HUMANHEAD mdl: Added support for saving strings passed in events
case D_EVENT_STRING:
str = reinterpret_cast<char *>( dataPtr );
savefile->Write( str, MAX_STRING_LEN );
size += MAX_STRING_LEN;
break;
// HUMANHEAD END
default:
break;
}
}
assert( size == event->eventdef->GetArgSize() );
assert(size == (int)event->eventdef->GetArgSize());
event = event->eventNode.Next();
}
}
@@ -706,11 +739,16 @@ void idEvent::Restore( idRestoreGame *savefile ) {
byte* dataPtr;
idEvent* event;
const char* format;
// RB: for missing D_EVENT_STRING
idStr s;
// RB end
savefile->ReadInt(num);
for ( i = 0; i < num; i++ ) {
if ( FreeEvents.IsListEmpty() ) {
for (i = 0; i < num; i++)
{
if (FreeEvents.IsListEmpty())
{
gameLocal.Error("idEvent::Restore : No more free events");
}
@@ -723,72 +761,101 @@ void idEvent::Restore( idRestoreGame *savefile ) {
// read the event name
savefile->ReadString(name);
event->eventdef = idEventDef::FindEvent(name);
if ( !event->eventdef ) {
if (event->eventdef == NULL)
{
savefile->Error("idEvent::Restore: unknown event '%s'", name.c_str());
return;
}
// read the classtype
savefile->ReadString(name);
event->typeinfo = idClass::GetClass(name);
if ( !event->typeinfo ) {
if (event->typeinfo == NULL)
{
savefile->Error("idEvent::Restore: unknown class '%s' on event '%s'", name.c_str(), event->eventdef->GetName());
return;
}
savefile->ReadObject(event->object);
// read the args
savefile->ReadInt(argsize);
if ( argsize != event->eventdef->GetArgSize() ) {
savefile->Error( "idEvent::Restore: arg size (%d) doesn't match saved arg size(%d) on event '%s'", event->eventdef->GetArgSize(), argsize, event->eventdef->GetName() );
if (argsize != (int)event->eventdef->GetArgSize())
{
// RB: fixed wrong formatting
savefile->Error("idEvent::Restore: arg size (%zd) doesn't match saved arg size(%zd) on event '%s'", event->eventdef->GetArgSize(), argsize, event->eventdef->GetName());
// RB end
}
if ( argsize ) {
if (argsize)
{
event->data = eventDataAllocator.Alloc(argsize);
format = event->eventdef->GetArgFormat();
assert(format);
for ( j = 0, size = 0; j < event->eventdef->GetNumArgs(); ++j) {
for (j = 0, size = 0; j < event->eventdef->GetNumArgs(); ++j)
{
dataPtr = &event->data[event->eventdef->GetArgOffset(j)];
switch( format[ j ] ) {
switch (format[j])
{
case D_EVENT_FLOAT:
savefile->ReadFloat(*reinterpret_cast<float*>(dataPtr));
size += sizeof( float );
// RB: 64 bit fix, changed sizeof( float ) to sizeof( intptr_t )
size += sizeof(intptr_t);
// RB end
break;
case D_EVENT_INTEGER:
// RB: 64 bit fix
savefile->ReadInt(*reinterpret_cast<int*>(dataPtr));
size += sizeof(intptr_t);
break;
// RB end
case D_EVENT_ENTITY:
case D_EVENT_ENTITY_NULL:
savefile->ReadInt( *reinterpret_cast<int *>( dataPtr ) );
size += sizeof( int );
// RB: 64 bit fix, changed alignment to sizeof( intptr_t )
reinterpret_cast<idEntityPtr<idEntity>*>(dataPtr)->Restore(savefile);
size += sizeof(intptr_t);
// RB end
break;
case D_EVENT_VECTOR:
savefile->ReadVec3(*reinterpret_cast<idVec3*>(dataPtr));
size += sizeof( idVec3 );
// RB: 64 bit fix, changed sizeof( int ) to E_EVENT_SIZEOF_VEC
size += E_EVENT_SIZEOF_VEC;
// RB end
break;
#if 1
// RB: added missing D_EVENT_STRING case
case D_EVENT_STRING:
savefile->ReadString(s);
//idStr::Copynz(reinterpret_cast<char *>( dataPtr ), s, s.Length() );
//size += s.Length();
idStr::Copynz(reinterpret_cast<char*>(dataPtr), s, MAX_STRING_LEN);
size += MAX_STRING_LEN;
break;
// RB end
#endif
case D_EVENT_TRACE:
savefile->ReadBool(*reinterpret_cast<bool*>(dataPtr));
size += sizeof(bool);
if ( *reinterpret_cast<bool *>( dataPtr ) ) {
if (*reinterpret_cast<bool*>(dataPtr))
{
size += sizeof(trace_t);
trace_t& t = *reinterpret_cast<trace_t*>(dataPtr + sizeof(bool));
RestoreTrace(savefile, t);
if ( t.c.material ) {
if (t.c.material)
{
size += MAX_STRING_LEN;
str = reinterpret_cast<char*>(dataPtr + sizeof(bool) + sizeof(trace_t));
savefile->Read(str, MAX_STRING_LEN);
}
}
break;
// HUMANHEAD mdl: Added support for saving strings passed in events
case D_EVENT_STRING:
str = reinterpret_cast<char *>( dataPtr );
savefile->Read( str, MAX_STRING_LEN );
size += MAX_STRING_LEN;
break;
// HUMANHEAD END
default:
break;
}
}
assert( size == event->eventdef->GetArgSize() );
} else {
assert(size == (int)event->eventdef->GetArgSize());
}
else
{
event->data = NULL;
}
}
+6 -3
View File
@@ -22,6 +22,9 @@ Event are used for scheduling tasks and for linking script commands.
#define MAX_EVENTS 4096
// stack size of idVec3, aligned to native pointer size
#define E_EVENT_SIZEOF_VEC ((sizeof(idVec3) + (sizeof(intptr_t) - 1)) & ~(sizeof(intptr_t) - 1))
//HUMANHEAD: aob - needed for networking to send the least amount of bits
extern const int MAX_EVENTS_NUM_BITS;
//HUMANHEAD END
@@ -50,7 +53,7 @@ public:
const char *GetName( void ) const;
const char *GetArgFormat( void ) const;
unsigned int GetFormatspecIndex( void ) const;
char GetReturnType( void ) const;
int GetReturnType( void ) const;
int GetEventNum( void ) const;
int GetNumArgs( void ) const;
size_t GetArgSize( void ) const;
@@ -87,7 +90,7 @@ public:
~idEvent();
static idEvent *Alloc( const idEventDef *evdef, int numargs, va_list args );
static void CopyArgs( const idEventDef *evdef, int numargs, va_list args, int data[ D_EVENT_MAXARGS ] );
static void CopyArgs( const idEventDef *evdef, int numargs, va_list args, intptr_t data[ D_EVENT_MAXARGS ] );
void Free( void );
void Schedule( idClass *object, const idTypeInfo *cls, int time );
@@ -152,7 +155,7 @@ ID_INLINE unsigned int idEventDef::GetFormatspecIndex( void ) const {
idEventDef::GetReturnType
================
*/
ID_INLINE char idEventDef::GetReturnType( void ) const {
ID_INLINE int idEventDef::GetReturnType( void ) const {
return returnType;
}
+22 -3
View File
@@ -672,7 +672,9 @@ void idInterpreter::CallEvent( const function_t *func, int argsize ) {
varEval_t var;
int pos;
int start;
int data[ D_EVENT_MAXARGS ];
// RB: 64 bit fixes, changed int to intptr_t
intptr_t data[D_EVENT_MAXARGS];
// RB end
const idEventDef *evdef;
const char *format;
@@ -686,6 +688,9 @@ void idInterpreter::CallEvent( const function_t *func, int argsize ) {
start = localstackUsed - argsize;
var.intPtr = ( int * )&localstack[ start ];
eventEntity = GetEntity( *var.entityNumberPtr );
static int testme;
testme = *var.entityNumberPtr;
if ( !eventEntity || !eventEntity->RespondsTo( *evdef ) ) {
if ( eventEntity && developer.GetBool() ) {
@@ -707,6 +712,7 @@ void idInterpreter::CallEvent( const function_t *func, int argsize ) {
gameLocal.program.ReturnInteger(0);
break;
case D_EVENT_FLOAT :
gameLocal.program.ReturnFloat( 0 );
break;
@@ -740,12 +746,17 @@ void idInterpreter::CallEvent( const function_t *func, int argsize ) {
switch( format[ i ] ) {
case D_EVENT_INTEGER :
var.intPtr = (int*)&localstack[start + pos];
data[ i ] = int( *var.floatPtr );
// RB: fixed data alignment
//data[ i ] = int( *var.floatPtr );
(*(int*)&data[i]) = int(*var.floatPtr);
// RB end
break;
case D_EVENT_FLOAT :
var.intPtr = ( int * )&localstack[ start + pos ];
( *( float * )&data[ i ] ) = *var.floatPtr;
static float value;
value = (*(float*)&data[i]);
break;
case D_EVENT_VECTOR :
@@ -869,7 +880,9 @@ void idInterpreter::CallSysEvent( const function_t *func, int argsize ) {
varEval_t source;
int pos;
int start;
int data[ D_EVENT_MAXARGS ];
// RB: 64 bit fixes, changed int to intptr_t
intptr_t data[D_EVENT_MAXARGS];
// RB end
const idEventDef *evdef;
const char *format;
@@ -1989,9 +2002,14 @@ bool idInterpreter::Execute( void ) {
case OP_PUSH_V:
var_a = GetVariable(st->a);
// RB: 64 bit fix, changed individual pushes with PushVector
/*
Push( *reinterpret_cast<int *>( &var_a.vectorPtr->x ) );
Push( *reinterpret_cast<int *>( &var_a.vectorPtr->y ) );
Push( *reinterpret_cast<int *>( &var_a.vectorPtr->z ) );
*/
PushVector(*var_a.vectorPtr);
// RB end
break;
case OP_PUSH_OBJ:
@@ -2014,3 +2032,4 @@ bool idInterpreter::Execute( void ) {
return threadDying;
}
+16 -5
View File
@@ -5,7 +5,7 @@
#define __SCRIPT_INTERPRETER_H__
#define MAX_STACK_DEPTH 64
#define LOCALSTACK_SIZE 6144
#define LOCALSTACK_SIZE (6144 * 2)
typedef struct prstack_s {
int s;
@@ -33,10 +33,11 @@ private:
idThread *thread;
void PushVector(const idVec3& vector);
void PopParms( int numParms );
void PushString( const char *string );
public://HUMANHEAD: aob - so we can pass parms in manually
void Push( int value );
void Push( intptr_t value );
private://HUMANHEAD: aob - undo the public declaration
const char *FloatToString( float value );
void AppendString( idVarDef *def, const char *from );
@@ -115,12 +116,12 @@ ID_INLINE void idInterpreter::PopParms( int numParms ) {
idInterpreter::Push
====================
*/
ID_INLINE void idInterpreter::Push( int value ) {
ID_INLINE void idInterpreter::Push(intptr_t value ) {
if ( localstackUsed + sizeof( int ) > LOCALSTACK_SIZE ) {
Error( "Push: locals stack overflow\n" );
}
*( int * )&localstack[ localstackUsed ] = value;
localstackUsed += sizeof( int );
*(intptr_t*)&localstack[localstackUsed] = value;
localstackUsed += sizeof(intptr_t);
}
/*
@@ -248,4 +249,14 @@ ID_INLINE void idInterpreter::NextInstruction( int position ) {
instructionPointer = position - 1;
}
ID_INLINE void idInterpreter::PushVector(const idVec3& vector)
{
if (localstackUsed + E_EVENT_SIZEOF_VEC > LOCALSTACK_SIZE)
{
Error("Push: locals stack overflow\n");
}
*(idVec3*)&localstack[localstackUsed] = vector;
localstackUsed += E_EVENT_SIZEOF_VEC;
}
#endif /* !__SCRIPT_INTERPRETER_H__ */
+22 -23
View File
@@ -16,23 +16,23 @@ static int globalOutputRunningSize = 0;
// simple types. function types are dynamically allocated
idTypeDef type_void( ev_void, &def_void, "void", 0, NULL );
idTypeDef type_scriptevent( ev_scriptevent, &def_scriptevent, "scriptevent", sizeof( void * ), NULL );
idTypeDef type_namespace( ev_namespace, &def_namespace, "namespace", sizeof( void * ), NULL );
idTypeDef type_scriptevent(ev_scriptevent, &def_scriptevent, "scriptevent", sizeof(intptr_t), NULL);
idTypeDef type_namespace(ev_namespace, &def_namespace, "namespace", sizeof(intptr_t), NULL);
//HUMANHEAD: aob - changed types to inherited types
idTypeDefString type_string( ev_string, &def_string, "string", MAX_STRING_LEN, NULL );
idTypeDefFloat type_float( ev_float, &def_float, "float", sizeof( float ), NULL );
idTypeDefVector type_vector( ev_vector, &def_vector, "vector", sizeof( idVec3 ), NULL );
idTypeDefEntity type_entity( ev_entity, &def_entity, "entity", sizeof( int * ), NULL ); // stored as entity number pointer
idTypeDefFloat type_float( ev_float, &def_float, "float", sizeof(intptr_t), NULL );
idTypeDefVector type_vector( ev_vector, &def_vector, "vector", E_EVENT_SIZEOF_VEC, NULL );
idTypeDefEntity type_entity( ev_entity, &def_entity, "entity", sizeof(intptr_t), NULL ); // stored as entity number pointer
//HUMANHEAD END
idTypeDef type_field( ev_field, &def_field, "field", sizeof( void * ), NULL );
idTypeDef type_function( ev_function, &def_function, "function", sizeof( void * ), &type_void );
idTypeDef type_virtualfunction( ev_virtualfunction, &def_virtualfunction, "virtual function", sizeof( int ), NULL );
idTypeDef type_pointer( ev_pointer, &def_pointer, "pointer", sizeof( void * ), NULL );
idTypeDef type_object( ev_object, &def_object, "object", sizeof( int * ), NULL ); // stored as entity number pointer
idTypeDef type_jumpoffset( ev_jumpoffset, &def_jumpoffset, "<jump>", sizeof( int ), NULL ); // only used for jump opcodes
idTypeDef type_argsize( ev_argsize, &def_argsize, "<argsize>", sizeof( int ), NULL ); // only used for function call and thread opcodes
idTypeDef type_field( ev_field, &def_field, "field", sizeof(intptr_t), NULL );
idTypeDef type_function( ev_function, &def_function, "function", sizeof(intptr_t), &type_void );
idTypeDef type_virtualfunction( ev_virtualfunction, &def_virtualfunction, "virtual function", sizeof(intptr_t), NULL );
idTypeDef type_pointer( ev_pointer, &def_pointer, "pointer", sizeof(intptr_t), NULL );
idTypeDef type_object( ev_object, &def_object, "object", sizeof(intptr_t), NULL ); // stored as entity number pointer
idTypeDef type_jumpoffset( ev_jumpoffset, &def_jumpoffset, "<jump>", sizeof(intptr_t), NULL ); // only used for jump opcodes
idTypeDef type_argsize( ev_argsize, &def_argsize, "<argsize>", sizeof(intptr_t), NULL ); // only used for function call and thread opcodes
//HUMANHEAD: aob - changed types to inherited types
idTypeDefBool type_boolean( ev_boolean, &def_boolean, "boolean", sizeof( int ), NULL );
idTypeDefBool type_boolean( ev_boolean, &def_boolean, "boolean", sizeof(intptr_t), NULL );
//HUMANHEAD END
idVarDef def_void( &type_void );
@@ -1342,23 +1342,21 @@ idVarDef *idProgram::AllocDef( idTypeDef *type, const char *name, idVarDef *scop
scope->value.functionPtr->locals += type->Size();
} else if ( scope->TypeDef()->Inherits( &type_object ) ) {
idTypeDef newtype(ev_field, NULL, "float field", 0, &type_float);
idTypeDef *type = GetType( newtype, true );
// RB: changed local type to ftype
idTypeDef* ftype = GetType(newtype, true);
// set the value to the variable's position in the object
def->value.ptrOffset = scope->TypeDef()->Size();
// make automatic defs for the vectors elements
// origin can be accessed as origin_x, origin_y, and origin_z
sprintf(element, "%s_x", def->Name());
def_x = AllocDef( type, element, scope, constant );
def_x = AllocDef(ftype, element, scope, constant);
sprintf(element, "%s_y", def->Name());
def_y = AllocDef( type, element, scope, constant );
def_y->value.ptrOffset = def_x->value.ptrOffset + type_float.Size();
def_y = AllocDef(ftype, element, scope, constant);
def_y->value.ptrOffset = def_x->value.ptrOffset + sizeof(float);
sprintf(element, "%s_z", def->Name());
def_z = AllocDef( type, element, scope, constant );
def_z->value.ptrOffset = def_y->value.ptrOffset + type_float.Size();
def_z = AllocDef(ftype, element, scope, constant);
def_z->value.ptrOffset = def_y->value.ptrOffset + sizeof(float);
// RB end
} else {
// make automatic defs for the vectors elements
// origin can be accessed as origin_x, origin_y, and origin_z
@@ -2257,6 +2255,7 @@ idProgram::ReturnEntity
*/
void idProgram::ReturnEntity( idEntity *ent ) {
if ( ent ) {
assert(ent->entityNumber + 1 <= MAX_GENTITIES);
*returnDef->value.entityNumberPtr = ent->entityNumber + 1;
} else {
*returnDef->value.entityNumberPtr = 0;
+1
View File
@@ -346,6 +346,7 @@ typedef union varEval_s {
int argSize;
varEval_s *evalPtr;
int ptrOffset;
INT_PTR highPtr;
} varEval_t;
class idVarDef {
+132 -16
View File
@@ -122,6 +122,11 @@ void idMaterial::CommonInit() {
decalInfo.end[1] = 0;
decalInfo.end[2] = 0;
decalInfo.end[3] = 0;
#ifdef PREY
subviewClass = SC_MIRROR;
directPortalDistance = 0;
#endif
}
/*
@@ -279,20 +284,20 @@ static infoParm_t infoParms[] = {
{"nosteps", 0, SURF_NOSTEPS, 0 }, // no footsteps
// material types for particle, sound, footstep feedback
{"metal", 0, SURFTYPE_METAL, 0 }, // metal
{"stone", 0, SURFTYPE_STONE, 0 }, // stone
{"flesh", 0, SURFTYPE_FLESH, 0 }, // flesh
{"wood", 0, SURFTYPE_WOOD, 0 }, // wood
{"cardboard", 0, SURFTYPE_CARDBOARD, 0 }, // cardboard
{"liquid", 0, SURFTYPE_LIQUID, 0 }, // liquid
{"glass", 0, SURFTYPE_GLASS, 0 }, // glass
{"tile", 0, SURFTYPE_TILE, 0 }, // tile
{"matter_metal", 0, SURFTYPE_METAL, 0 }, // metal
{"matter_stone", 0, SURFTYPE_STONE, 0 }, // stone
{"matter_flesh", 0, SURFTYPE_FLESH, 0 }, // flesh
{"matter_wood", 0, SURFTYPE_WOOD, 0 }, // wood
{"matter_cardboard", 0, SURFTYPE_CARDBOARD, 0 }, // cardboard
{"matter_liquid", 0, SURFTYPE_LIQUID, 0 }, // liquid
{"matter_glass", 0, SURFTYPE_GLASS, 0 }, // glass
{"matter_tile", 0, SURFTYPE_TILE, 0 }, // tile
{"wallwalk", 0, SURFTYPE_WALLWALK, 0 }, // wallwalk surface
{"altmetal", 0, SURFTYPE_ALTMETAL, 0 }, // alternate metal
{"matter_altmetal", 0, SURFTYPE_ALTMETAL, 0 }, // alternate metal
{"forcefield", 0, SURFTYPE_FORCEFIELD, 0 }, // forcefield material
{"pipe", 0, SURFTYPE_PIPE, 0 }, // pipe
{"spirit", 0, SURFTYPE_SPIRIT, 0 }, // spirit material
{"chaff", 0, SURFTYPE_CHAFF, 0 }, // chaff material
{"matter_pipe", 0, SURFTYPE_PIPE, 0 }, // pipe
{"matter_spirit", 0, SURFTYPE_SPIRIT, 0 }, // spirit material
{"matter_chaff", 0, SURFTYPE_CHAFF, 0 }, // chaff material
};
#else
static infoParm_t infoParms[] = {
@@ -1937,6 +1942,18 @@ void idMaterial::ParseMaterial( idLexer &src ) {
SetMaterialFlag(MF_FORCESHADOWS);
continue;
}
#ifdef PREY
// HUMANHEAD PCF: explicitly skip collision clip for alpha-coverage surfaces.
else if (!token.Icmp("skipClip")) {
SetMaterialFlag(MF_SKIPCLIP);
continue;
}
// HUMANHEAD bjk: don't cull tris with the light bounds.
else if (!token.Icmp("lightWholeMesh")) {
SetMaterialFlag(MF_LIGHT_WHOLE_MESH);
continue;
}
#endif
// overlay / decal suppression
else if (!token.Icmp("noOverlays")) {
allowOverlays = false;
@@ -2037,11 +2054,14 @@ void idMaterial::ParseMaterial( idLexer &src ) {
src.ReadTokenOnLine(&token);
if (!token.Icmp("entity")) {
entityGui = 1;
} else if ( !token.Icmp( "entity2" ) ) {
}
else if (!token.Icmp("entity2")) {
entityGui = 2;
} else if ( !token.Icmp( "entity3" ) ) {
}
else if (!token.Icmp("entity3")) {
entityGui = 3;
} else {
}
else {
gui = uiManager->FindGui(token.c_str(), true);
}
continue;
@@ -2072,6 +2092,17 @@ void idMaterial::ParseMaterial( idLexer &src ) {
src.ParseRestOfLine(renderBump);
continue;
}
#ifdef PREY
else if (!token.Icmp("glowmap")) {
src.ReadTokenOnLine(&token);
continue;
}
else if (!token.Icmp("highres")) {
continue;
}
#endif
// diffusemap for stage shortcut
else if (!token.Icmp("diffusemap")) {
str = R_ParsePastImageProgram(src);
@@ -2110,6 +2141,9 @@ void idMaterial::ParseMaterial( idLexer &src ) {
// discrete
surfaceFlags |= SURF_DISCRETE;
#ifdef PREY
surfaceFlags |= SURF_NOIMPACT;
#endif
contentFlags &= ~CONTENTS_SOLID;
// sort decal
@@ -2117,8 +2151,89 @@ void idMaterial::ParseMaterial( idLexer &src ) {
// noShadows
SetMaterialFlag(MF_NOSHADOWS);
#ifdef PREY
coverage = MC_TRANSLUCENT;
allowOverlays = false;
#endif
continue;
}
#ifdef PREY
// HUMANHEAD tmj: render this subview as a skybox portal.
else if (!token.Icmp("skyboxPortal")) {
sort = SS_SUBVIEW;
coverage = MC_OPAQUE;
subviewClass = SC_PORTAL_SKYBOX;
continue;
}
// HUMANHEAD CJR: render this subview as a direct portal, with distance-cull expression.
else if (!token.Icmp("directPortal")) {
sort = SS_SUBVIEW;
coverage = MC_OPAQUE;
subviewClass = SC_PORTAL;
directPortalDistance = ParseExpressionPriority(src, 4);
continue;
}
else if (!token.Icmp("DECAL_ALPHATEST_MACRO")) {
surfaceFlags |= SURF_NOIMPACT | SURF_DISCRETE;
contentFlags &= ~CONTENTS_SOLID;
sort = SS_DECAL;
SetMaterialFlag(MF_NOSHADOWS);
coverage = MC_TRANSLUCENT;
allowOverlays = false;
continue;
}
else if (!token.Icmp("SCORCH_MACRO") || !token.Icmp("OVERLAY_MACRO")) {
SetMaterialFlag(MF_POLYGONOFFSET);
polygonOffset = 1;
surfaceFlags |= SURF_NOIMPACT | SURF_DISCRETE;
contentFlags &= ~CONTENTS_SOLID;
sort = SS_DECAL;
SetMaterialFlag(MF_NOSHADOWS);
coverage = MC_TRANSLUCENT;
allowOverlays = false;
continue;
}
else if (!token.Icmp("GLASS_MACRO")) {
coverage = MC_TRANSLUCENT;
SetMaterialFlag(MF_NOSHADOWS);
pd->forceOverlays = true;
contentFlags &= ~CONTENTS_OPAQUE;
surfaceFlags = (surfaceFlags & ~SURF_TYPE_MASK) | SURFTYPE_GLASS;
sort = SS_MEDIUM;
continue;
}
else if (!token.Icmp("ALPHA_MACRO")) {
coverage = MC_TRANSLUCENT;
SetMaterialFlag(MF_NOSHADOWS);
surfaceFlags |= SURF_NOIMPACT;
cullType = CT_TWO_SIDED;
continue;
}
else if (!token.Icmp("EFFECT_MACRO")) {
coverage = MC_TRANSLUCENT;
SetMaterialFlag(MF_NOSHADOWS);
contentFlags &= ~CONTENTS_SOLID;
surfaceFlags |= SURF_NOIMPACT;
cullType = CT_TWO_SIDED;
continue;
}
else if (!token.Icmp("SPRITE_MACRO")) {
surfaceFlags |= SURF_DISCRETE;
contentFlags &= ~CONTENTS_SOLID;
SetMaterialFlag(MF_NOSHADOWS);
coverage = MC_TRANSLUCENT;
deform = DFRM_SPRITE;
cullType = CT_TWO_SIDED;
continue;
}
else if (!token.Icmp("SKYBOX_MACRO")) {
SetMaterialFlag(MF_NOSHADOWS | MF_NOSELFSHADOW);
allowOverlays = false;
coverage = MC_OPAQUE;
surfaceFlags |= SURF_NOIMPACT | SURF_NOFRAGMENT;
continue;
}
#endif
else if (token == "{") {
// create the new stage
ParseStage(src, trpDefault);
@@ -2162,7 +2277,8 @@ void idMaterial::ParseMaterial( idLexer &src ) {
if (pd->parseStages[i].texture.texgen != TG_EXPLICIT) {
if (firstGen == TG_EXPLICIT) {
firstGen = pd->parseStages[i].texture.texgen;
} else if ( firstGen != pd->parseStages[i].texture.texgen ) {
}
else if (firstGen != pd->parseStages[i].texture.texgen) {
common->Warning("material '%s' has multiple stages with a texgen", GetName());
break;
}
+44 -6
View File
@@ -42,6 +42,15 @@ class idCinematic;
class idUserInterface;
class idMegaTexture;
#ifdef PREY
// HUMANHEAD tmj: type of subview that this surface represents
typedef enum {
SC_MIRROR,
SC_PORTAL,
SC_PORTAL_SKYBOX,
} subviewClass_t;
#endif
// moved from image.h for default parm
typedef enum {
TF_LINEAR,
@@ -133,6 +142,10 @@ typedef enum {
EXP_REG_GLOBAL6,
EXP_REG_GLOBAL7,
#ifdef PREY
EXP_REG_DISTANCE, // HUMANHEAD: CJR
#endif
EXP_REG_NUM_PREDEFINED
} expRegister_t;
@@ -266,6 +279,10 @@ typedef enum {
MF_NOSELFSHADOW = BIT(4),
MF_NOPORTALFOG = BIT(5), // this fog volume won't ever consider a portal fogged out
MF_EDITOR_VISIBLE = BIT(6), // in use (visible) per editor
#ifdef PREY
MF_USESDISTANCE = BIT(7), // HUMANHEAD pdm: distance optimization
MF_LIGHT_WHOLE_MESH = BIT(8), // HUMANHEAD bjk: don't cull tris with light bounds
#endif
MF_SKIPCLIP = BIT(9)
} materialFlags_t;
@@ -415,6 +432,11 @@ public:
// used for bumpy-specular
const shaderStage_t* GetBumpStage(void) const;
#ifdef PREY
// HUMANHEAD tmj: returns how the subview should be rendered (mirror/portal/skybox)
subviewClass_t GetSubviewClass(void) const { return subviewClass; }
#endif
// returns true if the material will draw anything at all. Triggers, portals,
// etc, will not have anything to draw. A not drawn surface can still castShadow,
// which can be used to make a simplified shadow hull for a complex object set
@@ -476,8 +498,10 @@ public:
materialCoverage_t Coverage(void) const { return coverage; }
// returns true if this material takes precedence over other in coplanar cases
bool HasHigherDmapPriority( const idMaterial &other ) const { return ( IsDrawn() && !other.IsDrawn() ) ||
( Coverage() < other.Coverage() ); }
bool HasHigherDmapPriority(const idMaterial& other) const {
return (IsDrawn() && !other.IsDrawn()) ||
(Coverage() < other.Coverage());
}
// returns a idUserInterface if it has a global gui, or NULL if no gui
idUserInterface* GlobalGui(void) const { return gui; }
@@ -486,8 +510,10 @@ public:
// necessary to prevent mutliple gui surfaces, mirrors, autosprites, and some other
// special effects from being combined into a single surface
// guis, merging sprites or other effects, mirrors and remote views are always discrete
bool IsDiscrete( void ) const { return ( entityGui || gui || deform != DFRM_NONE || sort == SS_SUBVIEW ||
( surfaceFlags & SURF_DISCRETE ) != 0 ); }
bool IsDiscrete(void) const {
return (entityGui || gui || deform != DFRM_NONE || sort == SS_SUBVIEW ||
(surfaceFlags & SURF_DISCRETE) != 0);
}
// Normally, dmap chops each surface by every BSP boundary, then reoptimizes.
// For gigantic polygons like sky boxes, this can cause a huge number of planar
@@ -513,8 +539,10 @@ public:
// implicitly no-shadows lights (ambients, fogs, etc) will never cast shadows
// but individual light entities can also override this value
bool LightCastsShadows() const { return TestMaterialFlag( MF_FORCESHADOWS ) ||
( !fogLight && !ambientLight && !blendLight && !TestMaterialFlag( MF_NOSHADOWS ) ); }
bool LightCastsShadows() const {
return TestMaterialFlag(MF_FORCESHADOWS) ||
(!fogLight && !ambientLight && !blendLight && !TestMaterialFlag(MF_NOSHADOWS));
}
// fog lights, blend lights, ambient lights, etc will all have to have interaction
// triangles generated for sides facing away from the light as well as those
@@ -635,6 +663,10 @@ public:
bool IsPortalSky() const { return portalSky; };
void AddReference();
#ifdef PREY
int GetDirectPortalDistance() const { return directPortalDistance; } // HUMANHEAD CJR
#endif
private:
// parse the entire material
void CommonInit();
@@ -665,6 +697,9 @@ private:
void CheckForConstantRegisters();
private:
#ifdef PREY
subviewClass_t subviewClass; // HUMANHEAD tmj: Type of subview this surface points to
#endif
idStr desc; // description
idStr renderBump; // renderbump command options, without the "renderbump" at the start
@@ -678,6 +713,9 @@ private:
int spectrum; // for invisible writing, used for both lights and surfaces
#ifdef PREY
int directPortalDistance; // HUMANHEAD: Distance at which direct render portals are drawn
#endif
float polygonOffset;
int contentFlags; // content flags