Removing member var -> error?

Started by
45 comments, last by ms291052 20 years, 3 months ago
I have a class, THING, that is currently storing a bunch of information, including a MESH class. My problem began when I decided it seemed logical to store the mesh data (verts, indices, planes) in the MESH class, instead of the THING class. All of this worked fine, compiled fine, et al, but at runtime it began throwing System.NullReferenceException for whatever reason. Ok, so I go back through the code and make 100% sure that there are no references to any of the three variables I removed from the THING class, and there aren''t. After a while debugging I''ve found that my program doesn''t seem to like me removing one specific line, WORD Indices[99999], which I''ve flagged in the code below (I didn''t realize it but my indices were still using ghetto hard-coded arrays). Here''s my current THING class:

class THING
{
public:
	LPDIRECT3DDEVICE9 pd3dDevice;
	DWORD       ID;
	DWORD       CreationTime;
	DWORD       Flags;
	MESH        Mesh;
	char*       MeshFile;
protected:
	D3DXVECTOR3 Velocity;
	D3DXVECTOR3 Position;
	D3DXVECTOR3 Orientation;
	D3DXVECTOR3 RotVelocity;


public:
	int          Type;
	D3DXVECTOR3  CenterOfMass;
        D3DXPLANE*   Planes; //Doesn''t mind me removing this

        MODELVERTEX* Vertices; // or this

	WORD         Indices[99999]; //but removing this is bad

	int          NumVerts;
	int          NumFaces;
	BoundingSphere  root;
	int MaxHealth;
	int Health;

//Functions and blah blah blah...

};
And here''s how I want it:

class THING
{
public:
	LPDIRECT3DDEVICE9 pd3dDevice;
	DWORD       ID;
	DWORD       CreationTime;
	DWORD       Flags;
	MESH        Mesh;
	char*       MeshFile;
protected:
	D3DXVECTOR3 Velocity;
	D3DXVECTOR3 Position;
	D3DXVECTOR3 Orientation;
	D3DXVECTOR3 RotVelocity;


public:
	int          Type;
	D3DXVECTOR3  CenterOfMass;
	int          NumVerts;
	int          NumFaces;
	BoundingSphere  root;
	int MaxHealth;
	int Health;

//Functions and blah blah blah...

};
Any ideas as to what this is? I even did a search for "Indices" in VC++, and manually checked EVERY time that word came up, and there was no dereferencing pointers, or calling anything at all!
Advertisement
So commenting out WORD Indices[] breaks the code?

Can we see some code using THING ?

That would probably help some.



~V''lion

Bugle4d
~V'lionBugle4d
Did you try a clean build of your program?
Clean build meaning rebuild (deleting all *.obj and all)? If so, then yes.

As for some code using thing, exactly what do you need? I have several THINGs in my code right now. Not too many however, I believe that it''s just the player, the level, and a pointer/array to ten items (only four of which are used, I believe). This is all stored in a vector<thING*> called g_Things and I have THING* g_Player Initialized in my Init code. If there''s any specific bit of code you need to see please ask, as I need all the help I can get, however I have several thousand lines of code revolving around that class, and a couple hundred that use that class directly. Anyway, the most relevant code I can think to show is below:

All member functions of THING
vector<THING*> extern g_Things;void AddMessage(char*);THING::THING(){	ID = g_Things.size();}THING::THING(LPDIRECT3DDEVICE9 pd3dd, char* file = "", D3DXVECTOR3 p = D3DXVECTOR3(0.0f, 0.0f, 0.0f), int t = TT_THING){	ID = g_Things.size();	Health = MaxHealth = 100;	Velocity = Orientation = D3DXVECTOR3(0.0f, 0.0f, 0.0f);	pd3dDevice = pd3dd;	MeshFile = file;	Position = p;	Type = t;	m_CurWeapon = -1;	Mesh = MESH();	Mesh.InitMesh(pd3dDevice, MeshFile);	CreateSpheres();}THING::~THING(){	SAFE_RELEASE(pd3dDevice);}void THING::SetVelocity(D3DXVECTOR3 v){	Velocity = v;}D3DXVECTOR3 THING::GetVelocity(){	return Velocity;}void THING::SetPosition(D3DXVECTOR3 p){	Position = p;	Mesh.m_Pos = p;}D3DXVECTOR3 THING::GetPosition(){	if(this == NULL)		return D3DXVECTOR3(0.0f, 0.0f, 0.0f);	return Position;}void THING::SetOrientation(D3DXVECTOR3 o){	Orientation = o;	Mesh.m_Pitch = o.x;	Mesh.m_Yaw = o.y;	Mesh.m_Roll = o.z;}D3DXVECTOR3 THING::GetOrientation(){	return Orientation;}void THING::SetMesh(char* file){	MeshFile = &(*file);	Mesh.InitMesh(pd3dDevice, file);}char* THING::GetMesh(){	return MeshFile;}void THING::Update(float elapsed, bool gravity){	if(fabsf(Velocity.x) < 0.001f)		Velocity.x = 0.0f;	if(fabsf(Velocity.y) < 0.001f)		Velocity.y = 0.0f;	if(fabsf(Velocity.z) < 0.001f)		Velocity.z = 0.0f;	Position += Velocity*elapsed;	Mesh.m_Pos = Position;	if(Health > MaxHealth) Health = MaxHealth;	if(Health < 0) Health = 0;}void THING::Render(){	if(Type != TT_ROOM)		Mesh.RenderMesh();	else		Mesh.RenderMesh(D3DCULL_NONE);}void THING::CreateSpheres(int level){	root.level = 1;	NumVerts = Mesh.m_NumVertices;	D3DXComputeBoundingSphere(&Mesh.m_Vertices[0].pos, Mesh.m_NumVertices, sizeof(MODELVERTEX), &root.center, &root.radius);}void THING::Event(DWORD event, DWORD sender, bool issender, void* param){	switch(event)	{		case EVENT_NULL:		{		} break;		case EVENT_TOUCHED:		{			AddMessage("Two things just touched!");		} break;		case EVENT_DAMAGED:		{			int amt = *(int*)(param);			Health -= amt;			if(Health <= 0)			{				Health = 0;				this->Event(EVENT_KILLED, sender, issender, 0);			}			if(Health >= MaxHealth)			Health = MaxHealth;		} break;		case EVENT_KILLED:		{			//...		} break;		case EVENT_RESPAWN:		{			//...		} break;		case EVENT_CREATED:		{			//...		} break;		case EVENT_FIRE:		{			//...		} break;	}}


Init code: (ACTOR is a derived class from THING)
ACTOR Player = ACTOR(g_pd3dDevice, "meshes//player.x", D3DXVECTOR3(0.0f, 2.44f, 10.0f));g_Player = &Playerg_Things.push_back(&Player);


Part of MESH::InitMesh that intializes data of vertices, indices, and faces:
	if(m_Vertices)		delete[] m_Vertices;	if(m_Indices)		delete[] m_Indices;	if(m_Faces)		delete[] m_Faces;	m_Vertices = 0;	m_Faces = 0;	m_Indices = 0;	m_Vertices = new MODELVERTEX[m_pMesh->GetNumVertices()];	m_Faces = new D3DXPLANE[m_pMesh->GetNumFaces()];	m_Indices = new WORD[m_pMesh->GetNumFaces()*3];	byte *ptr=NULL;	DWORD numVerts;	m_NumVertices = numVerts = m_pMesh->GetNumVertices();	DWORD fvf=m_pMesh->GetFVF();	DWORD vertSize=D3DXGetFVFVertexSize(fvf);	WORD* indices;	hr = m_pMesh->LockVertexBuffer(D3DLOCK_READONLY,(void**)&ptr);	if(FAILED(hr)) FatalError();	hr = m_pMesh->LockIndexBuffer(D3DLOCK_READONLY, (void**)&indices);	if(FAILED(hr)) FatalError();	m_NumFaces = m_pMesh->GetNumFaces();	for (DWORD i=0;i<numVerts;i++)	{		m_Vertices[i] = *(MODELVERTEX*)(ptr);		m_CenterOfMass += m_Vertices[i].pos;		ptr+=vertSize;	}	m_pMesh->UnlockVertexBuffer();	for(unsigned int i=0;i<m_pMesh->GetNumFaces();i++)	{		m_Indices[i*3] = indices[i*3];		m_Indices[i*3+1] = indices[i*3+1];		m_Indices[i*3+2] = indices[i*3+2];		D3DXPLANE temp;		D3DXVECTOR3 t0 = m_Vertices[m_Indices[3*i]].pos;		D3DXVECTOR3 t1 = m_Vertices[m_Indices[3*i + 1]].pos;		D3DXVECTOR3 t2 = m_Vertices[m_Indices[3*i + 2]].pos;		D3DXPlaneFromPoints(&temp, &t0, &t1, &t2);		m_Faces[i] = temp;	}	m_CenterOfMass /= m_NumVertices*1.0f;	m_pMesh->UnlockIndexBuffer();


I have a lot more waiting, just ask. Thank you a thousand times for your help and time!
Sorry for above coloring problems, GameDev's source boxes don't seem to be 100% effective.

Edited to add another note (rather not waste bandwidth with another post). Whenever I delete that line, it gives me the error, but in the debugger, the System.NullReferenceException points to some bogus place in a completely different class file (that has NO interaction whatsoever with either THING nor MESH). It also begins saying that it can't find media file àx%%%%%%%\n#### or something (not sure about the actually ASCII, but it's definately random garbage).

[edited by - ms291052 on January 3, 2004 12:50:39 AM]
Check for all uses of Indicies.

My bump tells me that you are walking off the end of the array somewhere.

I''ve seen similiar weird random errors and they come from bad memory accesses.

Also: check all your new''s and delete''s.

Perhaps you are walking off into Indicies space?

What you could do is step through the program.

Focus on the spot where the media file error comes in.
It might be associated with that.
~V'lionBugle4d
Total uses of THING::Indices = 0
Total uses of Mesh::m_Indices = 12

I''m disinclined to believe that it has anything to do with overwriting anything, as that array is never used for anything. For the same reason, I don''t think I could ''walk off'' into its space, as I''m not using it, and ideally, it wouldn''t have any space to walk in to. The media errors seem to me to be completely unrelated but I shall atleast try to do a step-by-step and try to pinpoint exactly what''s going on. Thanks for all your help!
Well, THING::Planes and THING::Vertices are both pointers, but THING::Indices is a static array -- all 99999 elements are a part of the THING structure, so its size is += 2*99999 (2=sizeof WORD). This could be related to the reason it alone causes your program to fail.

Also the error could be not with Indices, but by sheer chance you don't get an exception if it's in THING. That would mean you just have a memory error elsewhere and you need to debug.

What happens if you move Indices to MESH but you keep it in THING as well? First put it in MESH but use the THING one, and ignore the mesh one. Then stop using the thing one and use the mesh's, without deleting the thing one.

~CGameProgrammer( );

-- Post screenshots of your projects. 100+ posts already in the archives.

[edited by - CGameProgrammer on January 4, 2004 4:51:43 AM]
~CGameProgrammer( );Developer Image Exchange -- New Features: Upload screenshots of your games (size is unlimited) and upload the game itself (up to 10MB). Free. No registration needed.
I've successfully created my desired MESH class, all that's left is that damn Indices[99999] in the THING class. I do, however realize it's insane size, which is why I'm trying so hard to clear that artifact from my THING class. As of now MESH::m_Indices is the only reference being used throughout the program. THING::Indices is not used at all, but the program complains if I remove it.

Edited to state that in the MESH class Indices is indeed a WORD*, not a WORD[].

[edited by - ms291052 on January 4, 2004 6:19:26 AM]
Another run through the debugger reveals this:
Memory Address: 003950bc lAllocID=1 dwSize=000047f8, ReturnAddr=03903796 (pid=000006ec)Memory Address: 0039b2b4 lAllocID=9 dwSize=00000bd0, ReturnAddr=038fe1e9 (pid=000006ec)Memory Address: 00393084 lAllocID=10 dwSize=00000008, ReturnAddr=038fe289 (pid=000006ec)Memory Address: 0039bebc lAllocID=11 dwSize=00000140, ReturnAddr=03902f45 (pid=000006ec)Memory Address: 0039c2cc lAllocID=20 dwSize=000006bc, ReturnAddr=0390f12f (pid=000006ec)Memory Address: 003998ec lAllocID=22 dwSize=00001008, ReturnAddr=0390478b (pid=000006ec)Memory Address: 00393044 lAllocID=24 dwSize=00000008, ReturnAddr=039048bc (pid=000006ec)Memory Address: 03ac0064 lAllocID=26 dwSize=00003500, ReturnAddr=03903796 (pid=000006ec)Memory Address: 0039c9bc lAllocID=27 dwSize=00000198, ReturnAddr=03903796 (pid=000006ec)Memory Address: 0039c034 lAllocID=28 dwSize=00000030, ReturnAddr=03903796 (pid=000006ec)Memory Address: 03ac359c lAllocID=29 dwSize=00001020, ReturnAddr=03903796 (pid=000006ec)


Could a memory leak have anything to do with the problem? If so (or even if not) does anyone know how I can tell which variables are being stored at these memory addresses so that I can make sure to delete them?

This topic is closed to new replies.

Advertisement